我的程序应该将二进制文件编码为base 64。 一切正常,直到EOF。我有麻烦添加' ='在输出字符串的末尾。
只有在读取最后一个字节时才会发生这种情况。它应该填补空白空间。这是我的代码,每当我必须添加一个或两个' ='时才会检测到。
Read:
mov eax,3 ; Specify sys_read call
mov ebx,0 ; Specify File Descriptor 0: Standard Input
mov ecx,Bytes ; Pass offset of the buffer to read to
mov edx,BYTESLEN ; Pass number of bytes to read at one pass
int 80h ; Call sys_read to fill the buffer
mov ebp,eax ; Save # of bytes read from file for later
cmp rax,1 ; If EAX=0, sys_read reached EOF on stdin
je MissingTwoByte ; Jump If Equal (to 1, from compare)
cmp rax,2 ; If EAX=0, sys_read reached EOF on stdin
je MissingOneByte ; Jump If Equal (to 2, from compare)
cmp eax,0 ; If EAX=0, sys_read reached EOF on stdin
je Done ; Jump If Equal (to 0, from compare)
所以在我的:MissingOneByte和:MissingTwoByte函数中,我应该添加Bytes my' =',对吧?我怎样才能做到这一点?
答案 0 :(得分:2)
在我之前的回答中..代码应该总是吃3个字节,用零填充,然后修复/修补结果!
即。对于单个输入字节0x44
,Bytes
需要设置为44 00 00
(第一个44
由sys_read
设置,其他两个需要通过代码清除)。您将获得错误的转化结果RAAA
,然后您需要将其修补为正确的RA==
。
即
SECTION .bss
BYTESLEN equ 3 ; 3 bytes of real buffer are needed
Bytes: resb BYTESLEN + 5; real buffer +5 padding (total 8B)
B64output: resb 4+4 ; 4 bytes are real output buffer
; +4 bytes are padding (total 8B)
SECTION .text
;...
Read:
mov eax,3 ; Specify sys_read call
xor ebx,ebx ; Specify File Descriptor 0: Standard Input
mov ecx,Bytes ; Pass offset of the buffer to read to
mov edx,BYTESLEN ; Pass number of bytes to read at one pass
int 80h ; Call sys_read to fill the buffer
test eax,eax
jl ReadingError ; OS has problem, system "errno" is set
mov ebp,eax ; Save # of bytes read from file for later
jz Done ; 0 bytes read, no more input
; eax = 1, 2, 3
mov [ecx + eax],ebx ; clear padding bytes
; ^^ this is a bit nasty EBX reuse, works only for STDIN (0)
; for any file handle use fixed zero: mov word [ecx+eax],0
call ConvertBytesToB64Output ; convert to Base64 output
; overwrite last two/one/none characters based on how many input
; bytes were read (B64output+3+1 = B64output+4 => beyond 4 chars)
mov word [B64output + ebp + 1], '=='
;TODO store B64output where you wish
cmp ebp,3
je Read ; if 3 bytes were read, loop again
; 1 or 2 bytes will continue with "Done:"
Done:
; ...
ReadingError:
; ...
ConvertBytesToB64Output:
; ...
ret
再次写作简短,不关心性能。
使指令变得简单的技巧是在缓冲区末尾有足够的填充,所以你不必担心覆盖缓冲区之外的内存,然后你可以在每次输出后写两个'=='
,并且只需将它放在所需的位置(覆盖最后两个字符,或者最后一个字符,或者将它完全写在输出之外)到填充区域。
如果没有这个,很多if (length == 1/2/3) {...} else {...}
会爬进代码,保护内存写入,只覆盖输出缓冲区而已。
因此,请确保您了解我所做的工作及其工作原理,并为您自己的缓冲区添加足够的填充。
另外......!免责声明!:我实际上并不知道在base64输出结束时应该有多少=
,以及何时...那要由OP来研究base64定义。我只是展示了如何修复3B-> 4B转换的错误输出,它采用由零填充的较短输入。嗯,根据online BASE64 generator,它实际上可以作为我的代码...(输入%3)=> 0没有=
,1有两个=
,2有=
。