How to return 64bit (address)

Started by pjot, September 06, 2006, 12:44:00 AM

Previous topic - Next topic

pjot

Hi,



With Tru64Unix I try to pass a memory address to a library, but this address must be 64bit. With the new 64bit stuff, does the (address) function actually return 64 bit addresses? If not, I guess this is the way to set it up (Little Endian):



(setq var "bla")
(or (address var)(>> (address var) 32))


From the source in 'nl-string.c' it's kind of hard to see what the function returns, but I guess it's 32bit...



Peter

Lutz

#1
Yes, the library interface is still 32-bit both ways, calling and returning. But you should be able to make the call with 64-bit, by passing two args for each 64-bit number in the correct endian order.



For the return value we are still 32-bit, you could experiment trying 64-bit return by changing the return line of executeLibfunction() in file nl-import.c to: return(stuffInteger64(cdeclFunction(....)))



But I am not sure what: UINT cdeclFunction() is on your machine, if UINT is 64-bit.



Let me know if this works and we can make a change for TRU64



Lutz



ps: yes the return value of address is also 32-bit you could try stuffInteger64(...) here too. There are probably more places like this which could be treated differently in Tru64. I wonder if you can send me the output from the latest util/type.c again.

pjot

#2
Hi Lutz,



Compiling the 'types.c' delivers a small problem:


Quote
peter> cc -o types types.c

cc: Info: types.c, line 41: In this statement, type long double has the same representation as type double on this platform and is treated as a synonym for type double in this compilation mode. (longdoubleny1)

printf("long double %dn", sizeof(long double));

----------------------------------^


If I change it to 'double' then compiling works, but now we have duplicate lines in the code... Output:


Quote
peter> ./types            



type      bytes

---------------

char        1

char *      8

void *      8

short int   2

int         4

long        8

long int    8

long long   8

float       4

double      8

double          8

wchar_t     4



format input              output

--------------------------------

%d    0xffffffff         -1

%u    0xffffffff         4294967295

%d    0x7fffffffffffffff -1

%u    0x7fffffffffffffff 4294967295

%x    0x7fffffffffffffff ffffffff

%X    0x7fffffffffffffff ffffffff

%lld  0x7fffffffffffffff ld

%lld  0xFfffffffffffffff ld

%llu  0xFfffffffffffffff lu




What I actually want to do is passing a pointer to a char array, so like the C-type char *argv[].



In Linux I can do this:



(pack "ld ld ld" (address "one") (address "two")(address "three"))


But this seems to go wrong with Tru64Unix.



Peter

Lutz

#3
Normally in a 64-bit compile The *argv[] would be  a 64-bit pointer to an array of string pointers.



I remember in the compile in Tru64 we have: #pragma pointer_size short, so I assume you still have to deliver 32 bit addresses, but an array of it:



This makes and array of 32bit string pointers to the strings "one" "two" "three":


(set 'argv (pack "ld ld ld" (address "one") (address "two")(address "three")) )

and this is now the 32bit address you would pass to Tru64:


(address argv) => plug into:
(true64import-func (address argv))


Lutz



ps: I will #ifdef the 'long double' to 'double' in types.c for Tru64

pjot

#4
Hm, some further experiments learn things should work OK in Tru64:



void txt(char* arg[])
{
printf("%sn", *arg);
}


cc -shared -o lib.so lib.c



Now I have a SO with a function which I can import. In my newLisp code I do the regular thing:



(set 'y "bla")
(set 'z (pack "ld" (address y) ))
(txt (address z))


This delivers the 'bla' to be printed. OK. Well. It's not newLisp then. I hacked the sourcecode of the target library, and I found that the coredump actually takes place in a function called 'XrmInitialize()'.



This is an X-function, allocating resources for window management.



Now could it be possible, in your point of view, that such an allocation of systemresources could take place in a 64bit address space, while newLisp is compiled for a 32bit address space, so this will deliver a conflict resulting into the coredump? (Because I import and call a function in a graphical library of Tru64Unix.)



If I create a regular C program and call this Xrm function, it's all OK. Therefore there must be an issue with the combination between newLisp and that particular function.



How do you see it? If my suspicion is correct, well, there's nothing to be done about it, but I'ld like to be wrong in this particular case :-)



Peter

Lutz

#5
QuoteNow could it be possible, in your point of view, that such an allocation of systemresources could take place in a 64bit address space, while newLisp is compiled for a 32bit address space, so this will deliver a conflict resulting into the coredump? (Because I import and call a function in a graphical library of Tru64Unix.)


Yes, this is exactly what is happening. There may be a different set of libraries available for 32-bit applications in Tru64? I.e. on some 64-Bit Linux you find 2 sets of libraries one 32- the other 4o 64-bit.



newLISP although it does now 64-bit integer arithmetik is still a 32-bit application handling address pointers as 32-bit entities.



Lutz

pjot

#6
Too bad, I was afraid so...



Still, the graphical library is opensource. I can try to recompile the complete library using the '-taso' flag as well:


Quote
      The -taso option, however, in addition to setting default addresses for

      text and data segments, also causes shared libraries linked outside the

      31-bit address space to be appropriately relocated by the loader.


I will give it a shot and let you know.



Thanks

Peter

pjot

#7
It doesn't work as the library itself has dependencies with other (closed source) libraries which are 64bit... too bad.



By the way, I really noticed a speed improvement of newLisp. Many programs run significantly faster now!



Regards

Peter

Lutz

#8
QuoteBy the way, I really noticed a speed improvement of newLisp. Many programs run significantly faster now!


yes, many 64-bit integer operations in arithmetic and other places internal to newLISP greatly benefit from your machines 64-bit registers.



Lutz

pjot

#9
Quote
newLISP although it does now 64-bit integer arithmetik is still a 32-bit application handling address pointers as 32-bit entities.


This is typically a situation where my infamous GTK-server can provide a way out: a 64bit GTK-server communicating over a STDIN channel or LIB interface against a 32bit compiled interpreter. Today I compiled my GTK-server on Tru64Unix - needed only some changes in the Makefile, and the 'snprintf' C function had to be replaced. Now it works in 64bit to my own surprise, and newLisp can import the GTK-server Shared Object with Xforms as backend :-).



So now I can use newLisp for GUI programming on Tru64Unix as well. The next release of GTK-server 2.1.2 will contain these fixes for Tru64 permanently.



Regards

Peter