purebasic.info
http://purebasic.info/phpBB3ex/

Магическое число, возвращаемое AvailableProgramOutput
http://purebasic.info/phpBB3ex/viewtopic.php?f=1&t=3897
Страница 1 из 1

Автор:  Smitis [ Сб июл 12, 2014 6:03 pm ]
Заголовок сообщения:  Магическое число, возвращаемое AvailableProgramOutput

Понадобилось тут перехватить вызов 7zip. Из консольного юникодного приложения. Причём юникодность тут роли не играет. И 7zip это лишь как пример. И вот такие интересные вещи происходят
Код:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
EnableExplicit
OpenConsole()
 
Define x.i
 
Define ArchFile.s = ProgramParameter()
;Define SevenZipExe.s = GetPathPart(ProgramFilename())+"7z.exe"
Define SevenZipExe.s = "7z.exe"
Define SevenZipCmd.s = "x -y -sccUTF-8 -- "+ArchFile
Define SevenZipRet.i
Define SevenZip.i
Define SevenZipOut.s
 
Define OutBytes.i, OutResult.i
Define OutBufferSize.i = 4194304
Define OutBuffer.i = AllocateMemory(OutBufferSize,#PB_Memory_NoClear)
Define LogH.i, LogFile.s = GetFilePart(ArchFile)+".log"
 
SevenZip = RunProgram(SevenZipExe,SevenZipCmd,"",#PB_Program_Open|#PB_Program_Read)
If SevenZip
        LogH = CreateFile(#PB_Any,LogFile)
        While ProgramRunning(SevenZip)
                OutBytes = AvailableProgramOutput(SevenZip)
                If OutBytes
                        PrintN("Out bytes: "+Str(OutBytes))
                        WriteStringN(LogH,"Out bytes: "+Str(OutBytes))
                        If OutBytes > OutBufferSize
                                OutBufferSize = OutBytes
                                OutBuffer = ReAllocateMemory(OutBuffer,OutBufferSize,#PB_Memory_NoClear)
                        EndIf
                        OutResult = ReadProgramData(SevenZip,OutBuffer,OutBufferSize)
                        PrintN("Out result: "+Str(OutResult))
                        WriteStringN(LogH,"Out result: "+Str(OutResult))
                        SevenZipOut = PeekS(OutBuffer,OutResult,#PB_UTF8)
                        WriteString(LogH,SevenZipOut,#PB_UTF8)
                        While Len(SevenZipOut)>0
                                x = FindString(SevenZipOut,#CRLF$)
                                If x=0 : x=Len(SevenZipOut) : EndIf
                                If Left(SevenZipOut,10) = "Extracting"
                                        ;PrintN("> "+Trim(Mid(SevenZipOut,11,x-11)))
                                EndIf
                                SevenZipOut = Mid(SevenZipOut,x+2)
                        Wend
                EndIf
                Delay(1)
        Wend
EndIf
PrintN("")
CloseFile(LogH)
FreeMemory(OutBuffer)
 


До какого-то момента всё нормально. Но по мере роста количества файлов в архиве, растёт, соответственно, объём выводимой информации.
Вообще, как в моём понимании, может быть неправильном, просходит получение данных при перехвате вывода - выводимые данные попадают в некий системный буфер и по мере заполнения буфера, отдаются вызывающей программе. Данные передаются небольшими "порциями", если их тут же выводить на экран, вывод будет идти рывками, по мере поступления данных. Вроде как тоже самое должно просходить и в PB. Но AvailableProgramOutput никогда не выдаёт число больше 4243. Это "магическое" число, возможно, и есть размер буфера. Но ReadProgramData возвращает совсем другое значение. С прилагаемым файлом 4243 и 290187 соответственно. Получается, AvailableProgramOutput врёт, а данные получаем не по мере заполнения буфера, а разом? И как тут понять, какой буфер для них нужно выделять?

П.С.
Почему-то не добавляются файлы 7z, глюк форума?

Вложения:
numnum10000-1.rar [522.82 KiB]
Скачиваний: 242

Страница 1 из 1 Часовой пояс: UTC + 3 часа
Powered by phpBB® Forum Software © phpBB Group
http://www.phpbb.com/