pharo icon indicating copy to clipboard operation
pharo copied to clipboard

enumerations for FFI callback-return-value ultimately needs to be an integer

Open bencoman opened this issue 2 years ago • 0 comments

Bug description When the return of an FFI callback is an enumeration, it ultimately needs to be converted to its integer value to marshalled back through the C ABI. For example, Libclang traverses its AST using a visitor callback, which uses an enum for its return value, defined in C like this...

enum CXChildVisitResult {
   CXChildVisit_Break,
   CXChildVisit_Continue,
   CXChildVisit_Recurse
};
CXChildVisitResult visitor(CXCursor cursor, CXCursor, CXClientData) {

The Libclang Pharo Bindings nicely define this as...

CXChildVisitResultEnum class >> enumDecl
     ^#(
         CXChildVisit_Break 0
         CXChildVisit_Continue 1
         CXChildVisit_Recurse 2
)            
CXCursorVisitorCb class >> fnSpec
	^#(CXChildVisitResultEnum (CXCursorStruct arg1, CXCursorStruct arg2, void *arg3))

Where the hierarchy is FFIEnumeration > FFIExternalEnumeration > CXExternalEnumeration > CXChildVisitResultEnum

The project README provides the simple example shown below, which however hanging the image when inspected...

LibClangExample stdlibHFunctions

Interupting with "CTRL-." displayed debugger with error "Instance of CXChildVisitResultEnum did not understand #asInteger" This is due to...

TFCallbackInvocation >> writeReturnValue: aValue
	self callback returnType "this is a TFIntType"
		callbackWrite: aValue "this is a CXChildVisitResultEnum(#CXChildVisit_Continue)"
		into: self returnHolder

leading two steps later to...

TFIntType >> write: anInteger into: anExternalAddress
	anExternalAddress 
             integerAt: 1 
             put: anInteger asInteger 
             size: self byteSize 
             signed: signed

where anInteger is a CXChildVisitResultEnum(#CXChildVisit_Continue) that doesn't understand #asInteger.

Adding...

CXExternalEnumeration>>asInteger
       ^ value asInteger

resolved the immediate issue, but probably this should be pushed up to FFIEnumeration where the "value" instance variable is defined.

To Reproduce Steps to reproduce the behavior:

  1. Load https://github.com/bencoman/libclang-pharo-bindings into Pharo 9.
  2. Inspect LibClangExample stdlibHFunctions which works
  3. Remove CXExternalEnumeration>>asInteger.
  4. Inspect LibClangExample stdlibHFunctions which hangs image. Press "CTRL-." to break.

Version information:

  • OS: Ubuntu 20 Windows Subsystem For Linux on Windows 11 (which btw displays WSL GUI apps on Windows display)
  • Pharo Version: 9 (64 bit) [note: using Pharo 9 since Pharo 10 is crashing when Iceberg tries to download]

Expected development cost $10. Fix is adding single one-line method, already tested and provided above. Its taken longer to write it up here.

P.S. Using this search I couldn't find which repo defined FFIEnumeration to submit a PR, sorry.

bencoman avatar Aug 21 '22 13:08 bencoman