Δευτέρα 7 Σεπτεμβρίου 2026

Version 15 Revision 41 - Assembler Upgrade

 The build-in assembler is a remastered version of  x86 assembler of Arne Elster 2007 / 2008.

The old version convert all code to ANSI and write to a byte array. Now I change this to Integer and I change the range of alphanumeric, adding codes from 128 to 32767.

We can use m2000 local variables and functions (not those with $) which declated as external. These external functions need to process it via @ which translate to number, the address of function. Using just the name without @ we do nothing because these functions are not exist as local variables. We call SysAllocStringLen using Call @SysAllocStringLen.

Using code for just calling from M2000 we can't use Extern clause, we have to declare the functions and then use the address of the function.

See asmdll and asmdll2 in Info file for how to use assembler to make dll files with import functions and export functions too.  Declare name Code address can be used  for changing the function signature also.


print "chapter 1"
print "strings returned as BSTR, as is or in a VARIANT"
print "We use SysAllocStringLen from oleaut32.dll"
Declare SysAllocStringLen Lib "oleaut32.SysAllocStringLen" {
Long OleStr, Long BLen
} As Long
Print "  - using Variant - Calling with variant as return value M2000 automatic pass an empty variant"
mycode=assembly({
push dword 14 ; Length of "Hello World"
lea eax, [data1]        
push eax
call @SysAllocStringLen ; @ read address of SysAllocStringLen()
mov edx, [esp + 4]       ; get the address of hidden empty variant
mov word [edx], 8        ; vt type = 8 (string)
mov dword [edx + 2], 0   ; Clear reserved fields (Offset 2)
mov dword [edx + 6], 0   ; Clear reserved fields (Offset 6)
mov [edx + 8], eax       ; Place the BSTR pointer into the Variant data (Offset 8)
mov dword [edx + 12], 0 ; Clear reserved fields (Offset 12)
; so now 16bytes returned via edx
ret 4
align 4
data1: dw "Hello World 𐐷" ; no need 0
})
declare HelloWorld code mycode(0) as variant
Print HelloWorld()
Print "  - using String - just return pointer to BSTR in eax"
mycode2=assembly({
push dword 14  ; Length of "Hello World"
lea eax, [data1]
push eax
call @SysAllocStringLen
; string BSTR pointer is in EAX
ret
align 4
data1: dw "Hello World 𐐷"
})


mycode2=assembly({
push dword 14  ; Length of "Hello World"
lea eax, [data1]
push eax
call @SysAllocStringLen
; string BSTR pointer is in EAX
ret
align 4
data1: dw "Hello World 𐐷"
})


declare HelloWorld2 code mycode2(0) as string
Print HelloWorld2()


print "chapter 2 - no need for SysAllocStringLen"
print "strings returned as pointer which have length depend of position of zero"
print "M2000 automatic produce BSTR from pointers"
print "1 - unicode string returned"
mycode3=assembly({
lea eax, [data1]
ret
align 4
data1: dw "بيانات Hello World 𐐷", 0
})
print "declared only by name of function HelloWorld3$"
declare HelloWorld3$ code mycode3(0)
Print HelloWorld3$()

print "declared as string pointer"
declare HelloWorld4 code mycode3(0) as string pointer
Print HelloWorld4()


print "2 - ansi string returned - name of function HelloWorld3"
mycode4=assembly({
lea eax, [بيانات] ; we can use arabic also...
ret
align 4
بيانات: db "Hello World", 0  ; we use db not dw for ansi
})
print "  delcared as string pointer ansi"
declare HelloWorld5 code mycode4(0) as string pointer ansi
Print HelloWorld5()
print "  delcared as ansi"
declare HelloWorld6 code mycode4(0) as ansi
Print HelloWorld6()

Δεν υπάρχουν σχόλια:

Δημοσίευση σχολίου

You can feel free to write any suggestion, or idea on the subject.