Einzelnem Byte Wert zuweisen
-
Hallo,
ich schreibe (oder versuche) gerade folgende Funktion:
procedure FSetValue( var Dest; TSize, Count: Integer; Values: array of const ); asm push edi mov edi, eax // let edi point to destination mov ebx, 0 // pointer-inc @@_loop: cmp ecx, edx // compare counter with count je @@_exit mov ecx, [ebp+20+ebx] mov [eax], ecx // move value to destination add ebx, [ebp+12] // plus Size inc ecx jmp @@_loop @@_exit: pop edi end;
Wenn man ein BoolArray beispielsweise hat, mit vier Bools, dann soll man die Prozedur so aufrufen können:
FSetValue( BoolAr, sizeof(Bool), 4, [true, false, false, true] );
Das Problem daran ist natürlich, dass ich immer direkt vier Bytes schreibe und dann ist immer gleich alles true ...
Wie kann ich das richtig lösen?
-
Wie kann ich das richtig lösen?
Indem man sich schon im Vorfeld ueberlegt, ob ein Element so eines Bool-Arrays nun 1,2 oder 4 Byte gross sein soll und gar nicht erst ein temporaeres Array vom "falschen" Datentyp erzeugt.
-
hellihjb schrieb:
Indem man sich schon im Vorfeld ueberlegt, ob ein Element so eines Bool-Arrays nun 1,2 oder 4 Byte gross sein soll und gar nicht erst ein temporaeres Array vom "falschen" Datentyp erzeugt.
Ich erzeuge ja kein Array vom "falschen" Datentyp. Die Angabe der Größe entspricht im Endeffekt immer sizeof(Type). Es muss sich nicht immer um bool`sche Werte handeln.
Die Frage die ich stellte bezieht sich ja auch eher darauf, wie ich einem einzelnen Byte eine Zuweisung machen kann.
-
FrEEzE2046 schrieb:
wie ich einem einzelnen Byte eine Zuweisung machen kann.
mov [eax], cl
Ich erzeuge ja kein Array vom "falschen" Datentyp. Die Angabe der Größe entspricht im Endeffekt immer sizeof(Type).
Wenn Ziel- und Quell-Array gleichen Datentyp haben kannst Du auch einfach size*count Bytes per "rep movsb/d" kopieren.
-
hellihjb schrieb:
Wenn Ziel- und Quell-Array gleichen Datentyp haben kannst Du auch einfach size*count Bytes per "rep movsb/d" kopieren.
Das will mir nicht so ganz gelingen. Könntest du mir vielleicht auf die Sprünge helfen?
push edi mov ds, eax // ds points to destination mov esi, eax mov eax, edx // Size mov ebx, ecx // Count mul ebx // Size * Count add esi, ebx // increment destination ( + size*count ) mov edx, [ebp+20] // edx points to source mov es, edx // es ... mov edi, edx add edi, ebx rep movsb pop edi
-
Um die Segmentregister brauchst Du Dich in einer 32Bit-Umgebung nicht zu kuemmern:
mov esi, [ebp+20] ; esi: Source mov edi, eax ; edi: Destination imul ecx, edx ; ecx: number of bytes= Size * Count rep movsb ; kopieren
effizienter:
mov ecx, eax shr ecx, 2 ; erst in 4er-Schritten kopieren jz rest rep movsd rest: mov ecx, eax and ecx, 3 ; dann den Rest jz skip rep movsb skip:
Bei grossen Daten ist es sinnvoll Alignment sicherzustellen.