most probably this is fine, I would not know why mmap and munmap should use a different lookup...
On 2012-11-16, at 10:40, Max Leske <[email protected]> wrote: > It seems I found a fix. I simply copied the code from the "mmap" call over to > "munmap". Can somebody (Igor?) *please* confirm that this is ok to do? My > tests are green but I'm really not sure about this… > > Here's the new code for NBMacExternalHeapManager>>unmap:length: > > NBMacExternalHeapManager >>unmap: addr length: len > > <primitive: #primitiveNativeCall module: #NativeBoostPlugin error: > errorCode> > > "unmap memory page" > > ^ NBFFICallout > cdecl: #( int (uint addr, ulong len) ) > emitCall: [:gen | | munmap | > munmap := NativeBoost forCurrentPlatform > getGlobalSymbolPointer: 'munmap'. > gen asm mov: munmap asUImm32 to: gen asm EAX. > gen asm call: gen asm EAX > ] > options: #( - optDirectProxyFnAddress ) > > > Cheers, > Max > > > On 16.11.2012, at 14:11, Max Leske <[email protected]> wrote: > >> A followup on the munmap issue: >> >> I think it has something to do with how NativeBoost does the lookup. I >> looked at the way that "mmap" is called and noticed that the selector >> #getGlobalSymbolPointer: is being used. Resolving "munmap" with this >> selector succeeds while doing >> >> NativeBoost loadSymbol: 'munmap' aName fromModule: -2 >> >> (which is what happens when the heap manager tries to call "munmap") results >> the stack trace shown below. >> >> I'll keep digging... >> >> >> On 15.11.2012, at 17:20, Max Leske <[email protected]> wrote: >> >>> Hi >>> >>> When NativeBoost tries to call munmap to free a page (happens because a >>> pointer I freed was the last reserved one in that page) it will throw a >>> NBFFICalloutError (every time) because (I think) it can't find the symbol. >>> I have absolutely no clue how to fix this so I'm in need of help. >>> >>> System: OS X 10.8.2 >>> Image: 1.4 >>> NativeBoost-Core: CamilloBruni.80 (Installed by using the latest >>> NBInstaller) >>> >>> Cheers, >>> Max >>> >>> Here's the stack: >>> >>> 15 November 2012 5:04:23.895 pm >>> >>> VM: Mac OS - intel - 1082 - NBCoInterpreter >>> NativeBoost-CogPlugin-IgorStasenko.14 uuid: >>> da3a649c-e2b2-bd4c-aa2f-9c2ebdb2658a Oct 26 2012, >>> StackToRegisterMappingCogit VMMaker-oscog-EstebanLorenzano.164 uuid: >>> d77dee73-00f5-4d00-847b-00646b08329d Oct 26 2012, >>> git://gitorious.org/cogvm/blessed.git Commit: >>> 48af8595004fd0ec3a3ac6d44c3d7516a87981ca Date: 2012-10-24 16:56:20 +0200 >>> By: Igor Stasenko <[email protected]> Jenkins build #131 >>> Image: Pharo1.4 [Latest update: #14457] >>> >>> NBFFICallout class>>signalError: >>> Receiver: NBFFICallout >>> Arguments and temporary variables: >>> errorCode: 1 >>> Receiver's instance variables: >>> superclass: NBNativeCodeGen >>> methodDict: a >>> MethodDictionary(#aliasForType:->(NBFFICallout>>#aliasForType: "a...etc... >>> format: 148 >>> instanceVariables: #('fnSpec' 'requestor' 'methodArgs' >>> 'coercionMayFail' 'callI...etc... >>> organization: ('type aliases' aliasForType:) >>> ('accessing' anonSpec: callType: c...etc... >>> subclasses: {NBNativeFunctionGen} >>> name: #NBFFICallout >>> classPool: a Dictionary(#CustomErrorCodes->a >>> Dictionary(600->'An instance of NB...etc... >>> sharedPools: nil >>> environment: a SystemDictionary(lots of globals) >>> category: #'NativeBoost-Core-FFI' >>> traitComposition: {} >>> localSelectors: nil >>> >>> NBFFICallout class(NBNativeCodeGen class)>>handleFailureIn:nativeCode: >>> Receiver: NBFFICallout >>> Arguments and temporary variables: >>> aContext: >>> NativeBoostMac32(NativeBoost)>>bootstrapLoadSymbol:ofLength:fromModul...etc... >>> aBlock: [:gen | gen useEmitCall; sender: sender; >>> parseOptions: anOptions; cdecl...etc... >>> method: >>> (NativeBoost>>#bootstrapLoadSymbol:ofLength:fromModule:into: "a >>> Compile...etc... >>> lastError: 1 >>> Receiver's instance variables: >>> superclass: NBNativeCodeGen >>> methodDict: a >>> MethodDictionary(#aliasForType:->(NBFFICallout>>#aliasForType: "a...etc... >>> format: 148 >>> instanceVariables: #('fnSpec' 'requestor' 'methodArgs' >>> 'coercionMayFail' 'callI...etc... >>> organization: ('type aliases' aliasForType:) >>> ('accessing' anonSpec: callType: c...etc... >>> subclasses: {NBNativeFunctionGen} >>> name: #NBFFICallout >>> classPool: a Dictionary(#CustomErrorCodes->a >>> Dictionary(600->'An instance of NB...etc... >>> sharedPools: nil >>> environment: a SystemDictionary(lots of globals) >>> category: #'NativeBoost-Core-FFI' >>> traitComposition: {} >>> localSelectors: nil >>> >>> NBFFICallout class>>cdecl:emitCall:options: >>> Receiver: NBFFICallout >>> Arguments and temporary variables: >>> functionSpec: #(#NBBootstrapUlong #(#byte #* #symbolName #, >>> #long #symbolLen #,...etc... >>> aCallEmittingBlock: [:gen | gen proxy callFn: >>> #ioLoadSymbol:OfLength:FromModule...etc... >>> anOptions: #(#- #optDirectProxyFnAddress >>> #optAllowExternalAddressPtr) >>> sender: >>> NativeBoostMac32(NativeBoost)>>bootstrapLoadSymbol:ofLength:fromModule:...etc... >>> Receiver's instance variables: >>> superclass: NBNativeCodeGen >>> methodDict: a >>> MethodDictionary(#aliasForType:->(NBFFICallout>>#aliasForType: "a...etc... >>> format: 148 >>> instanceVariables: #('fnSpec' 'requestor' 'methodArgs' >>> 'coercionMayFail' 'callI...etc... >>> organization: ('type aliases' aliasForType:) >>> ('accessing' anonSpec: callType: c...etc... >>> subclasses: {NBNativeFunctionGen} >>> name: #NBFFICallout >>> classPool: a Dictionary(#CustomErrorCodes->a >>> Dictionary(600->'An instance of NB...etc... >>> sharedPools: nil >>> environment: a SystemDictionary(lots of globals) >>> category: #'NativeBoost-Core-FFI' >>> traitComposition: {} >>> localSelectors: nil >>> >>> NativeBoostMac32(NativeBoost)>>bootstrapLoadSymbol:ofLength:fromModule:into: >>> Receiver: a NativeBoostMac32 >>> Arguments and temporary variables: >>> symbolName: 'munmap' >>> symbolLen: 6 >>> moduleHandle: -2 >>> returnValueBuffer: #[0 0 0 0 0 0 0 0] >>> Receiver's instance variables: >>> bootstrapping: false >>> insideCallback: nil >>> callbackCounterAddr: @ 16r5F74000 >>> extraRootsRegistry: a NBExtraRootsRegistry >>> rootsCell: @ 16r5F7402A >>> gateFunction: @ 16r5F74004 >>> heap: a NBMacExternalHeapManager >>> >>> NativeBoostMac32(NativeBoost)>>loadSymbol:fromModule: >>> Receiver: a NativeBoostMac32 >>> Arguments and temporary variables: >>> aSymbolName: 'munmap' >>> moduleName: -2 >>> bytes: #[0 0 0 0 0 0 0 0] >>> module: -2 >>> handle: nil >>> Receiver's instance variables: >>> bootstrapping: false >>> insideCallback: nil >>> callbackCounterAddr: @ 16r5F74000 >>> extraRootsRegistry: a NBExtraRootsRegistry >>> rootsCell: @ 16r5F7402A >>> gateFunction: @ 16r5F74004 >>> heap: a NBMacExternalHeapManager >>> >>> NativeBoostMac32(NativeBoostLinux32)>>loadSymbol:fromModule: >>> Receiver: a NativeBoostMac32 >>> Arguments and temporary variables: >>> aSymbolName: 'munmap' >>> moduleName: -2 >>> Receiver's instance variables: >>> bootstrapping: false >>> insideCallback: nil >>> callbackCounterAddr: @ 16r5F74000 >>> extraRootsRegistry: a NBExtraRootsRegistry >>> rootsCell: @ 16r5F7402A >>> gateFunction: @ 16r5F74004 >>> heap: a NBMacExternalHeapManager >>> >>> NativeBoost class>>loadSymbol:fromModule: >>> Receiver: NativeBoost >>> Arguments and temporary variables: >>> aSymbolName: 'munmap' >>> moduleName: -2 >>> Receiver's instance variables: >>> superclass: Object >>> methodDict: a >>> MethodDictionary(#CLibrary->(NativeBoost>>#CLibrary "a CompiledMe...etc... >>> format: 142 >>> instanceVariables: #('bootstrapping' 'insideCallback' >>> 'callbackCounterAddr' 'ex...etc... >>> organization: ('retrieving symbols' CLibrary VMModule >>> ioLoadFunction:from: ioLo...etc... >>> subclasses: {NativeBoostLinux32. NativeBoostWin32} >>> name: #NativeBoost >>> classPool: a Dictionary(#Current->a NativeBoostMac32 >>> #NBAnnouncer->an Announcer...etc... >>> sharedPools: an OrderedCollection(AJx86Registers >>> NativeBoostConstants) >>> environment: a SystemDictionary(lots of globals) >>> category: #'NativeBoost-Core' >>> traitComposition: {} >>> localSelectors: nil >>> >>> NBMacExternalHeapManager class(Object)>>nbGetSymbolAddress:module: >>> Receiver: NBMacExternalHeapManager >>> Arguments and temporary variables: >>> aName: 'munmap' >>> aModuleNameOrHandle: -2 >>> addr: nil >>> Receiver's instance variables: >>> superclass: NBExternalHeapManager >>> methodDict: a >>> MethodDictionary(#mapFlags->(NBMacExternalHeapManager>>#mapFlags ...etc... >>> format: 138 >>> instanceVariables: nil >>> organization: ('as yet unclassified' mapFlags >>> mmapLength:prot:flags:into: primA...etc... >>> subclasses: nil >>> name: #NBMacExternalHeapManager >>> classPool: nil >>> sharedPools: an OrderedCollection(NBMacConstants) >>> environment: a SystemDictionary(lots of globals) >>> category: #'NativeBoost-Mac' >>> traitComposition: {} >>> localSelectors: nil >>> >>> [:gen | >>> fnAddress := requestor nbGetSymbolAddress: fnSpec functionName module: >>> aModuleNameOrHandle. >>> fnAddress >>> ifNil: [self error: 'function unavailable']. >>> self optMayGC >>> ifTrue: [asm push: fnAddress asUImm32; >>> mov: NativeBoost callgateFunctionAddress >>> asUImm32 to: EAX; >>> call: EAX] >>> ifFalse: [asm mov: fnAddress asUImm32 to: EAX; >>> call: EAX]] in >>> NBFFICallout>>generateCall:module: >>> Receiver: a NBFFICallout >>> Arguments and temporary variables: >>> aModuleNameOrHandle: a NBFFICallout >>> fnAddress: -2 >>> gen: #(nil) >>> Receiver's instance variables: >>> asm: an AJx86Assembler >>> proxy: a NBInterpreterProxy >>> options: a Set(#optCdecl #optAllowByteArraysPtr >>> #optUseStackPointer #optReturnP...etc... >>> method: (NBMacExternalHeapManager>>#unmap:length: "a >>> CompiledMethod(355205120)"...etc... >>> fnSpec: a NBFnSpec >>> requestor: NBMacExternalHeapManager >>> methodArgs: an OrderedCollection('addr' 'len') >>> coercionMayFail: true >>> callInfo: an AJCdeclCallInfo >>> >>> BlockClosure>>valueWithPossibleArgs: >>> Receiver: [:gen | >>> fnAddress := requestor nbGetSymbolAddress: fnSpec functionName module: >>> aModuleNam...etc... >>> Arguments and temporary variables: >>> anArray: an Array(a NBFFICallout a NBInterpreterProxy an >>> AJx86Assembler) >>> Receiver's instance variables: >>> outerContext: NBFFICallout>>generateCall:module: >>> startpc: 91 >>> numArgs: 1 >>> >>> [aFunctionBodyBlock valueWithPossibleArgs: {self. proxy. asm}. >>> (self optEmitCall >>> or: [self optNoCleanup]) >>> ifTrue: [call disableCleanup]] in [:call | >>> self optNoAlignment >>> ifTrue: [call alignment: 1]. >>> self pushArguments. >>> coercionMayFail >>> ifTrue: [proxy ifFailedJumpTo: self failedLabel]. >>> asm >>> decorateWith: 'FFI: performing a call' >>> during: [aFunctionBodyBlock valueWithPossibleArgs: {self. >>> proxy. asm}. >>> (self optEmitCall >>> or: [self optNoCleanup]) >>> ifTrue: [call disableCleanup]]] in >>> NBFFICallout>>generateInstructions: >>> Receiver: a NBFFICallout >>> Arguments and temporary variables: >>> aFunctionBodyBlock: an AJCdeclCallInfo >>> call: [:gen | >>> fnAddress := requestor nbGetSymbolAddress: fnSpec functionName m...etc... >>> Receiver's instance variables: >>> asm: an AJx86Assembler >>> proxy: a NBInterpreterProxy >>> options: a Set(#optCdecl #optAllowByteArraysPtr >>> #optUseStackPointer #optReturnP...etc... >>> method: (NBMacExternalHeapManager>>#unmap:length: "a >>> CompiledMethod(355205120)"...etc... >>> fnSpec: a NBFnSpec >>> requestor: NBMacExternalHeapManager >>> methodArgs: an OrderedCollection('addr' 'len') >>> coercionMayFail: true >>> callInfo: an AJCdeclCallInfo >>> >>> BlockClosure>>ensure: >>> Receiver: [aFunctionBodyBlock valueWithPossibleArgs: {self. proxy. asm}. >>> (self optEmitCall >>> or: [...etc... >>> Arguments and temporary variables: >>> aBlock: [level := level - 1. >>> self >>> addInstruction: (AJInstructionDecoration n...etc... >>> complete: nil >>> returnValue: nil >>> Receiver's instance variables: >>> outerContext: [:call | >>> self optNoAlignment >>> ifTrue: [call alignment: 1]. >>> sel...etc... >>> startpc: 155 >>> numArgs: 0 >>> >>> AJx86Assembler>>decorateWith:during: >>> Receiver: an AJx86Assembler >>> Arguments and temporary variables: >>> annotation: 'FFI: performing a call' >>> aBlock: [aFunctionBodyBlock valueWithPossibleArgs: >>> {self. proxy. asm}. >>> (self o...etc... >>> Receiver's instance variables: >>> instructions: <<error during printing>> >>> >>> [:call | >>> self optNoAlignment >>> ifTrue: [call alignment: 1]. >>> self pushArguments. >>> coercionMayFail >>> ifTrue: [proxy ifFailedJumpTo: self failedLabel]. >>> asm >>> decorateWith: 'FFI: performing a call' >>> during: [aFunctionBodyBlock valueWithPossibleArgs: {self. >>> proxy. asm}. >>> (self optEmitCall >>> or: [self optNoCleanup]) >>> ifTrue: [call disableCleanup]]] in >>> NBFFICallout>>generateInstructions: >>> Receiver: a NBFFICallout >>> Arguments and temporary variables: >>> aFunctionBodyBlock: an AJCdeclCallInfo >>> call: [:gen | >>> fnAddress := requestor nbGetSymbolAddress: fnSpec functionName m...etc... >>> Receiver's instance variables: >>> asm: an AJx86Assembler >>> proxy: a NBInterpreterProxy >>> options: a Set(#optCdecl #optAllowByteArraysPtr >>> #optUseStackPointer #optReturnP...etc... >>> method: (NBMacExternalHeapManager>>#unmap:length: "a >>> CompiledMethod(355205120)"...etc... >>> fnSpec: a NBFnSpec >>> requestor: NBMacExternalHeapManager >>> methodArgs: an OrderedCollection('addr' 'len') >>> coercionMayFail: true >>> callInfo: an AJCdeclCallInfo >>> >>> AJx86Assembler>>performingCall:in: >>> Receiver: an AJx86Assembler >>> Arguments and temporary variables: >>> ci: an AJCdeclCallInfo >>> aBlock: [:call | >>> self optNoAlignment >>> ifTrue: [call alignment: 1]. >>> self push...etc... >>> Receiver's instance variables: >>> instructions: <<error during printing>> >>> >>> NBFFICallout>>foreignCall: >>> Receiver: a NBFFICallout >>> Arguments and temporary variables: >>> aBlock: [:call | >>> self optNoAlignment >>> ifTrue: [call alignment: 1]. >>> self push...etc... >>> Receiver's instance variables: >>> asm: an AJx86Assembler >>> proxy: a NBInterpreterProxy >>> options: a Set(#optCdecl #optAllowByteArraysPtr >>> #optUseStackPointer #optReturnP...etc... >>> method: (NBMacExternalHeapManager>>#unmap:length: "a >>> CompiledMethod(355205120)"...etc... >>> fnSpec: a NBFnSpec >>> requestor: NBMacExternalHeapManager >>> methodArgs: an OrderedCollection('addr' 'len') >>> coercionMayFail: true >>> callInfo: an AJCdeclCallInfo >>> >>> NBFFICallout>>generateInstructions: >>> Receiver: a NBFFICallout >>> Arguments and temporary variables: >>> aFunctionBodyBlock: [:gen | >>> fnAddress := requestor nbGetSymbolAddress: fnSpec ...etc... >>> instructions: nil >>> Receiver's instance variables: >>> asm: an AJx86Assembler >>> proxy: a NBInterpreterProxy >>> options: a Set(#optCdecl #optAllowByteArraysPtr >>> #optUseStackPointer #optReturnP...etc... >>> method: (NBMacExternalHeapManager>>#unmap:length: "a >>> CompiledMethod(355205120)"...etc... >>> fnSpec: a NBFnSpec >>> requestor: NBMacExternalHeapManager >>> methodArgs: an OrderedCollection('addr' 'len') >>> coercionMayFail: true >>> callInfo: an AJCdeclCallInfo >>> >>> NBFFICallout>>generate: >>> Receiver: a NBFFICallout >>> Arguments and temporary variables: >>> aFunctionBodyBlock: [:gen | >>> fnAddress := requestor nbGetSymbolAddress: fnSpec ...etc... >>> generatedCode: nil >>> Receiver's instance variables: >>> asm: an AJx86Assembler >>> proxy: a NBInterpreterProxy >>> options: a Set(#optCdecl #optAllowByteArraysPtr >>> #optUseStackPointer #optReturnP...etc... >>> method: (NBMacExternalHeapManager>>#unmap:length: "a >>> CompiledMethod(355205120)"...etc... >>> fnSpec: a NBFnSpec >>> requestor: NBMacExternalHeapManager >>> methodArgs: an OrderedCollection('addr' 'len') >>> coercionMayFail: true >>> callInfo: an AJCdeclCallInfo >>> >>> NBFFICallout>>generateCall:module: >>> Receiver: a NBFFICallout >>> Arguments and temporary variables: >>> functionSpec: #(#int #munmap #(#uint #addr #, #ulong #len)) >>> aModuleNameOrHandle: -2 >>> fnAddress: #(nil) >>> Receiver's instance variables: >>> asm: an AJx86Assembler >>> proxy: a NBInterpreterProxy >>> options: a Set(#optCdecl #optAllowByteArraysPtr >>> #optUseStackPointer #optReturnP...etc... >>> method: (NBMacExternalHeapManager>>#unmap:length: "a >>> CompiledMethod(355205120)"...etc... >>> fnSpec: a NBFnSpec >>> requestor: NBMacExternalHeapManager >>> methodArgs: an OrderedCollection('addr' 'len') >>> coercionMayFail: true >>> callInfo: an AJCdeclCallInfo >>> >>> [:gen | gen sender: sender; >>> cdecl; >>> generateCall: functionSpec module: aModuleName] in >>> NBFFICallout class>>cdecl:module: >>> Receiver: NBFFICallout >>> Arguments and temporary variables: >>> functionSpec: a NBFFICallout >>> aModuleName: #(#int #munmap #(#uint #addr #, #ulong #len)) >>> sender: -2 >>> gen: NBMacExternalHeapManager>>unmap:length: >>> Receiver's instance variables: >>> superclass: NBNativeCodeGen >>> methodDict: a >>> MethodDictionary(#aliasForType:->(NBFFICallout>>#aliasForType: "a...etc... >>> format: 148 >>> instanceVariables: #('fnSpec' 'requestor' 'methodArgs' >>> 'coercionMayFail' 'callI...etc... >>> organization: ('type aliases' aliasForType:) >>> ('accessing' anonSpec: callType: c...etc... >>> subclasses: {NBNativeFunctionGen} >>> name: #NBFFICallout >>> classPool: a Dictionary(#CustomErrorCodes->a >>> Dictionary(600->'An instance of NB...etc... >>> sharedPools: nil >>> environment: a SystemDictionary(lots of globals) >>> category: #'NativeBoost-Core-FFI' >>> traitComposition: {} >>> localSelectors: nil >>> >>> [bytes := aBlock >>> value: (self newForMethod: method)] in >>> NBFFICallout class(NBNativeCodeGen class)>>generateCode:andRetry: >>> Receiver: NBFFICallout >>> Arguments and temporary variables: >>> aBlock: [:gen | gen sender: sender; >>> cdecl; >>> generateCall: functionSpec mod...etc... >>> method: (NBMacExternalHeapManager>>#unmap:length: "a >>> CompiledMethod(355205120)"...etc... >>> bytes: #(nil) >>> Receiver's instance variables: >>> superclass: NBNativeCodeGen >>> methodDict: a >>> MethodDictionary(#aliasForType:->(NBFFICallout>>#aliasForType: "a...etc... >>> format: 148 >>> instanceVariables: #('fnSpec' 'requestor' 'methodArgs' >>> 'coercionMayFail' 'callI...etc... >>> organization: ('type aliases' aliasForType:) >>> ('accessing' anonSpec: callType: c...etc... >>> subclasses: {NBNativeFunctionGen} >>> name: #NBFFICallout >>> classPool: a Dictionary(#CustomErrorCodes->a >>> Dictionary(600->'An instance of NB...etc... >>> sharedPools: nil >>> environment: a SystemDictionary(lots of globals) >>> category: #'NativeBoost-Core-FFI' >>> traitComposition: {} >>> localSelectors: nil >>> >>> BlockClosure>>on:do: >>> Receiver: [bytes := aBlock >>> value: (self newForMethod: method)] >>> Arguments and temporary variables: >>> exception: NBRecursionDetect >>> handlerAction: [:ex | ex check: aMethod] >>> handlerActive: true >>> Receiver's instance variables: >>> outerContext: NBFFICallout class(NBNativeCodeGen >>> class)>>generateCode:andRetry:...etc... >>> startpc: 96 >>> numArgs: 0 >>> >>> NBRecursionDetect class>>in:during: >>> Receiver: NBRecursionDetect >>> Arguments and temporary variables: >>> aMethod: (NBMacExternalHeapManager>>#unmap:length: "a >>> CompiledMethod(355205120)...etc... >>> aBlock: [bytes := aBlock >>> value: (self newForMethod: method)] >>> Receiver's instance variables: >>> superclass: Notification >>> methodDict: a >>> MethodDictionary(#check:->(NBRecursionDetect>>#check: "a Compiled...etc... >>> format: 144 >>> instanceVariables: #('method') >>> organization: ('as yet unclassified' check: defaultAction >>> method signalForMetho...etc... >>> subclasses: nil >>> name: #NBRecursionDetect >>> classPool: nil >>> sharedPools: nil >>> environment: a SystemDictionary(lots of globals) >>> category: #'NativeBoost-Core-Errors' >>> traitComposition: {} >>> localSelectors: nil >>> >>> NBFFICallout class(NBNativeCodeGen class)>>generateCode:andRetry: >>> Receiver: NBFFICallout >>> Arguments and temporary variables: >>> aBlock: [:gen | gen sender: sender; >>> cdecl; >>> generateCall: functionSpec mod...etc... >>> retryCtx: NBMacExternalHeapManager>>unmap:length: >>> method: (NBMacExternalHeapManager>>#unmap:length: "a >>> CompiledMethod(355205120)"...etc... >>> newMethod: nil >>> args: nil >>> bytes: #(nil) >>> Receiver's instance variables: >>> superclass: NBNativeCodeGen >>> methodDict: a >>> MethodDictionary(#aliasForType:->(NBFFICallout>>#aliasForType: "a...etc... >>> format: 148 >>> instanceVariables: #('fnSpec' 'requestor' 'methodArgs' >>> 'coercionMayFail' 'callI...etc... >>> organization: ('type aliases' aliasForType:) >>> ('accessing' anonSpec: callType: c...etc... >>> subclasses: {NBNativeFunctionGen} >>> name: #NBFFICallout >>> classPool: a Dictionary(#CustomErrorCodes->a >>> Dictionary(600->'An instance of NB...etc... >>> sharedPools: nil >>> environment: a SystemDictionary(lots of globals) >>> category: #'NativeBoost-Core-FFI' >>> traitComposition: {} >>> localSelectors: nil >>> >>> NBFFICallout class(NBNativeCodeGen class)>>handleFailureIn:nativeCode: >>> Receiver: NBFFICallout >>> Arguments and temporary variables: >>> aContext: NBMacExternalHeapManager>>unmap:length: >>> aBlock: [:gen | gen sender: sender; >>> cdecl; >>> generateCall: functionSpec mod...etc... >>> method: (NBMacExternalHeapManager>>#unmap:length: "a >>> CompiledMethod(355205120)"...etc... >>> lastError: 502 >>> Receiver's instance variables: >>> superclass: NBNativeCodeGen >>> methodDict: a >>> MethodDictionary(#aliasForType:->(NBFFICallout>>#aliasForType: "a...etc... >>> format: 148 >>> instanceVariables: #('fnSpec' 'requestor' 'methodArgs' >>> 'coercionMayFail' 'callI...etc... >>> organization: ('type aliases' aliasForType:) >>> ('accessing' anonSpec: callType: c...etc... >>> subclasses: {NBNativeFunctionGen} >>> name: #NBFFICallout >>> classPool: a Dictionary(#CustomErrorCodes->a >>> Dictionary(600->'An instance of NB...etc... >>> sharedPools: nil >>> environment: a SystemDictionary(lots of globals) >>> category: #'NativeBoost-Core-FFI' >>> traitComposition: {} >>> localSelectors: nil >>> >>> NBFFICallout class>>cdecl:module: >>> Receiver: NBFFICallout >>> Arguments and temporary variables: >>> functionSpec: #(#int #munmap #(#uint #addr #, #ulong #len)) >>> aModuleName: -2 >>> sender: NBMacExternalHeapManager>>unmap:length: >>> Receiver's instance variables: >>> superclass: NBNativeCodeGen >>> methodDict: a >>> MethodDictionary(#aliasForType:->(NBFFICallout>>#aliasForType: "a...etc... >>> format: 148 >>> instanceVariables: #('fnSpec' 'requestor' 'methodArgs' >>> 'coercionMayFail' 'callI...etc... >>> organization: ('type aliases' aliasForType:) >>> ('accessing' anonSpec: callType: c...etc... >>> subclasses: {NBNativeFunctionGen} >>> name: #NBFFICallout >>> classPool: a Dictionary(#CustomErrorCodes->a >>> Dictionary(600->'An instance of NB...etc... >>> sharedPools: nil >>> environment: a SystemDictionary(lots of globals) >>> category: #'NativeBoost-Core-FFI' >>> traitComposition: {} >>> localSelectors: nil >>> >>> NBMacExternalHeapManager>>unmap:length: >>> Receiver: a NBMacExternalHeapManager >>> Arguments and temporary variables: >>> addr: 7380992 >>> len: 32768 >>> errorCode: 502 >>> Receiver's instance variables: >>> pages: a Dictionary(24981504->a NBMemoryPage 100089856->a >>> NBMemoryPage ) >>> freeBlocks: an IdentitySet(a NBMemoryBlock( @ 16r17D302E, >>> 17, free) a NBMemoryB...etc... >>> reservedBlocks: a Dictionary(24981504->a NBMemoryBlock( >>> @ 16r17D3000, 38) 24981...etc... >>> sema: a Semaphore() >>> >>> NBMacExternalHeapManager>>primFreePage: >>> Receiver: a NBMacExternalHeapManager >>> Arguments and temporary variables: >>> aMemoryPage: a NBMemoryPage >>> res: nil >>> Receiver's instance variables: >>> pages: a Dictionary(24981504->a NBMemoryPage 100089856->a >>> NBMemoryPage ) >>> freeBlocks: an IdentitySet(a NBMemoryBlock( @ 16r17D302E, >>> 17, free) a NBMemoryB...etc... >>> reservedBlocks: a Dictionary(24981504->a NBMemoryBlock( >>> @ 16r17D3000, 38) 24981...etc... >>> sema: a Semaphore() >>> >>> NBMacExternalHeapManager(NBExternalHeapManager)>>freePage: >>> Receiver: a NBMacExternalHeapManager >>> Arguments and temporary variables: >>> aMemoryPage: a NBMemoryPage >>> Receiver's instance variables: >>> pages: a Dictionary(24981504->a NBMemoryPage 100089856->a >>> NBMemoryPage ) >>> freeBlocks: an IdentitySet(a NBMemoryBlock( @ 16r17D302E, >>> 17, free) a NBMemoryB...etc... >>> reservedBlocks: a Dictionary(24981504->a NBMemoryBlock( >>> @ 16r17D3000, 38) 24981...etc... >>> sema: a Semaphore() >>> >>> [:page | >>> page length = aMemoryBlock length >>> ifTrue: [self freePage: page. >>> ^ true]. >>> nil] in >>> NBMacExternalHeapManager(NBExternalHeapManager)>>checkForFreePage: >>> Receiver: a NBMacExternalHeapManager >>> Arguments and temporary variables: >>> aMemoryBlock: a NBMemoryPage >>> page: a NBMemoryBlock( @ 16r70A000, 32768, free) >>> Receiver's instance variables: >>> pages: a Dictionary(24981504->a NBMemoryPage 100089856->a >>> NBMemoryPage ) >>> freeBlocks: an IdentitySet(a NBMemoryBlock( @ 16r17D302E, >>> 17, free) a NBMemoryB...etc... >>> reservedBlocks: a Dictionary(24981504->a NBMemoryBlock( >>> @ 16r17D3000, 38) 24981...etc... >>> sema: a Semaphore() >>> >>> BlockClosure>>cull: >>> Receiver: [:page | >>> page length = aMemoryBlock length >>> ifTrue: [self freePage: page. >>> ^ true]. >>> n...etc... >>> Arguments and temporary variables: >>> anArg: a NBMemoryPage >>> Receiver's instance variables: >>> outerContext: >>> NBMacExternalHeapManager(NBExternalHeapManager)>>checkForFreePage...etc... >>> startpc: 41 >>> numArgs: 1 >>> >>> Dictionary>>at:ifPresent: >>> Receiver: a Dictionary(24981504->a NBMemoryPage 100089856->a >>> NBMemoryPage ) >>> Arguments and temporary variables: >>> key: 7380992 >>> aBlock: [:page | >>> page length = aMemoryBlock length >>> ifTrue: [self freePage: p...etc... >>> assoc: 7380992->a NBMemoryPage >>> Receiver's instance variables: >>> tally: 2 >>> array: an Array(nil 100089856->a NBMemoryPage nil nil >>> 24981504->a NBMemoryPage)...etc... >>> >>> NBMacExternalHeapManager(NBExternalHeapManager)>>checkForFreePage: >>> Receiver: a NBMacExternalHeapManager >>> Arguments and temporary variables: >>> aMemoryBlock: a NBMemoryBlock( @ 16r70A000, 32768, free) >>> Receiver's instance variables: >>> pages: a Dictionary(24981504->a NBMemoryPage 100089856->a >>> NBMemoryPage ) >>> freeBlocks: an IdentitySet(a NBMemoryBlock( @ 16r17D302E, >>> 17, free) a NBMemoryB...etc... >>> reservedBlocks: a Dictionary(24981504->a NBMemoryBlock( >>> @ 16r17D3000, 38) 24981...etc... >>> sema: a Semaphore() >>> >>> NBMemoryBlock>>makeFreeFor: >>> Receiver: a NBMemoryBlock( @ 16r70A030, 32720, free) >>> Arguments and temporary variables: >>> heapManager: a NBMacExternalHeapManager >>> Receiver's instance variables: >>> left: a NBMemoryBlock( @ 16r70A000, 32768, free) >>> right: nil >>> address: 7381040 >>> length: 32720 >>> free: true >>> >>> [| block | >>> block := reservedBlocks >>> removeKey: address >>> ifAbsent: [self error: 'Unable to find a memory >>> block with given address']. >>> block makeFreeFor: self] in >>> NBMacExternalHeapManager(NBExternalHeapManager)>>free: >>> Receiver: a NBMacExternalHeapManager >>> Arguments and temporary variables: >>> address: 7381040 >>> block: a NBMemoryBlock( @ 16r70A030, 32720, free) >>> Receiver's instance variables: >>> pages: a Dictionary(24981504->a NBMemoryPage 100089856->a >>> NBMemoryPage ) >>> freeBlocks: an IdentitySet(a NBMemoryBlock( @ 16r17D302E, >>> 17, free) a NBMemoryB...etc... >>> reservedBlocks: a Dictionary(24981504->a NBMemoryBlock( >>> @ 16r17D3000, 38) 24981...etc... >>> sema: a Semaphore() >>> >>> [caught := true. >>> self wait. >>> blockValue := mutuallyExcludedBlock value] in Semaphore>>critical: >>> Receiver: a Semaphore() >>> Arguments and temporary variables: >>> <<error during printing> >>> Receiver's instance variables: >>> firstLink: nil >>> lastLink: nil >>> excessSignals: 0 >>> >>> BlockClosure>>ensure: >>> Receiver: [caught := true. >>> self wait. >>> blockValue := mutuallyExcludedBlock value] >>> Arguments and temporary variables: >>> aBlock: [caught >>> ifTrue: [self signal]] >>> complete: nil >>> returnValue: nil >>> Receiver's instance variables: >>> outerContext: Semaphore>>critical: >>> startpc: 42 >>> numArgs: 0 >>> >>> Semaphore>>critical: >>> Receiver: a Semaphore() >>> Arguments and temporary variables: >>> <<error during printing> >>> Receiver's instance variables: >>> firstLink: nil >>> lastLink: nil >>> excessSignals: 0 >>> >>> NBMacExternalHeapManager(NBExternalHeapManager)>>free: >>> Receiver: a NBMacExternalHeapManager >>> Arguments and temporary variables: >>> address: 7381040 >>> Receiver's instance variables: >>> pages: a Dictionary(24981504->a NBMemoryPage 100089856->a >>> NBMemoryPage ) >>> freeBlocks: an IdentitySet(a NBMemoryBlock( @ 16r17D302E, >>> 17, free) a NBMemoryB...etc... >>> reservedBlocks: a Dictionary(24981504->a NBMemoryBlock( >>> @ 16r17D3000, 38) 24981...etc... >>> sema: a Semaphore() >>> >>> >>> --- The full stack --- >>> NBFFICallout class>>signalError: >>> NBFFICallout class(NBNativeCodeGen class)>>handleFailureIn:nativeCode: >>> NBFFICallout class>>cdecl:emitCall:options: >>> NativeBoostMac32(NativeBoost)>>bootstrapLoadSymbol:ofLength:fromModule:into: >>> NativeBoostMac32(NativeBoost)>>loadSymbol:fromModule: >>> NativeBoostMac32(NativeBoostLinux32)>>loadSymbol:fromModule: >>> NativeBoost class>>loadSymbol:fromModule: >>> NBMacExternalHeapManager class(Object)>>nbGetSymbolAddress:module: >>> [:gen | >>> fnAddress := requestor nbGetSymbolAddress: fnSpec functionName module: >>> aModuleNameOrHandle. >>> fnAddress >>> ifNil: [self error: 'function unavailable']. >>> self optMayGC >>> ifTrue: [asm push: fnAddress asUImm32; >>> mov: NativeBoost callgateFunctionAddress >>> asUImm32 to: EAX; >>> call: EAX] >>> ifFalse: [asm mov: fnAddress asUImm32 to: EAX; >>> call: EAX]] in >>> NBFFICallout>>generateCall:module: >>> BlockClosure>>valueWithPossibleArgs: >>> [aFunctionBodyBlock valueWithPossibleArgs: {self. proxy. asm}. >>> (self optEmitCall >>> or: [self optNoCleanup]) >>> ifTrue: [call disableCleanup]] in [:call | >>> self optNoAlignment >>> ifTrue: [call alignment: 1]. >>> self pushArguments. >>> coercionMayFail >>> ifTrue: [proxy ifFailedJumpTo: self failedLabel]. >>> asm >>> decorateWith: 'FFI: performing a call' >>> during: [aFunctionBodyBlock valueWithPossibleArgs: {self. >>> proxy. asm}. >>> (self optEmitCall >>> or: [self optNoCleanup]) >>> ifTrue: [call disableCleanup]]] in >>> NBFFICallout>>generateInstructions: >>> BlockClosure>>ensure: >>> AJx86Assembler>>decorateWith:during: >>> [:call | >>> self optNoAlignment >>> ifTrue: [call alignment: 1]. >>> self pushArguments. >>> coercionMayFail >>> ifTrue: [proxy ifFailedJumpTo: self failedLabel]. >>> asm >>> decorateWith: 'FFI: performing a call' >>> during: [aFunctionBodyBlock valueWithPossibleArgs: {self. >>> proxy. asm}. >>> (self optEmitCall >>> or: [self optNoCleanup]) >>> ifTrue: [call disableCleanup]]] in >>> NBFFICallout>>generateInstructions: >>> AJx86Assembler>>performingCall:in: >>> NBFFICallout>>foreignCall: >>> NBFFICallout>>generateInstructions: >>> NBFFICallout>>generate: >>> NBFFICallout>>generateCall:module: >>> [:gen | gen sender: sender; >>> cdecl; >>> generateCall: functionSpec module: aModuleName] in >>> NBFFICallout class>>cdecl:module: >>> [bytes := aBlock >>> value: (self newForMethod: method)] in >>> NBFFICallout class(NBNativeCodeGen class)>>generateCode:andRetry: >>> BlockClosure>>on:do: >>> NBRecursionDetect class>>in:during: >>> NBFFICallout class(NBNativeCodeGen class)>>generateCode:andRetry: >>> NBFFICallout class(NBNativeCodeGen class)>>handleFailureIn:nativeCode: >>> NBFFICallout class>>cdecl:module: >>> NBMacExternalHeapManager>>unmap:length: >>> NBMacExternalHeapManager>>primFreePage: >>> NBMacExternalHeapManager(NBExternalHeapManager)>>freePage: >>> [:page | >>> page length = aMemoryBlock length >>> ifTrue: [self freePage: page. >>> ^ true]. >>> nil] in >>> NBMacExternalHeapManager(NBExternalHeapManager)>>checkForFreePage: >>> BlockClosure>>cull: >>> Dictionary>>at:ifPresent: >>> NBMacExternalHeapManager(NBExternalHeapManager)>>checkForFreePage: >>> NBMemoryBlock>>makeFreeFor: >>> [| block | >>> block := reservedBlocks >>> removeKey: address >>> ifAbsent: [self error: 'Unable to find a memory >>> block with given address']. >>> block makeFreeFor: self] in >>> NBMacExternalHeapManager(NBExternalHeapManager)>>free: >>> [caught := true. >>> self wait. >>> blockValue := mutuallyExcludedBlock value] in Semaphore>>critical: >>> BlockClosure>>ensure: >>> Semaphore>>critical: >>> NBMacExternalHeapManager(NBExternalHeapManager)>>free: >>> - - - - - - - - - - - - - - - >>> - - - - - - - - - - - - - - - - - - >>> NativeBoostMac32(NativeBoostLinux32)>>free: >>> NativeBoost class>>free: >>> NBExternalAddress>>free >>> [:pointer | pointer value free] in LimboCommand>>freePointers >>> Set>>do: >>> LimboCommand>>freePointers >>> [self freePointers] in LimboCommand>>run >>> BlockClosure>>ensure: >>> LimboCommand>>run >>> Limbo>>run:arguments: >>> Limbo>>runSh: >>> Limbo class>>runSh: >>> [limbo := Limbo runSh: '/bin/echo ' , arg] in >>> LimboTest>>testShellCommandWithNewLines >>> [aBlock value. >>> false] in LimboTest(TestCase)>>executeShould:inScopeOf: >>> BlockClosure>>on:do: >>> LimboTest(TestCase)>>executeShould:inScopeOf: >>> LimboTest(TestCase)>>shouldnt:raise: >>> LimboTest>>testShellCommandWithNewLines >>> LimboTest(TestCase)>>performTest >>> [self setUp. >>> self performTest] in LimboTest(TestCase)>>runCase >>> BlockClosure>>ensure: >>> LimboTest(TestCase)>>runCase >>> [(self class selector: testSelector) runCase] in LimboTest(TestCase)>>debug >>> BlockClosure>>ensure: >>> LimboTest(TestCase)>>debug >>> OBCmdRunTests>>execute >>> [:each | >>> (each isActive >>> and: [each isEnabled]) >>> ifTrue: [each execute. >>> ^ true]. >>> nil] in OBNodeCommandScan(OBCommandScan)>>processKeystroke:withNode:for: >>> OrderedCollection>>do: >>> OBNodeCommandScan(OBCommandScan)>>processKeystroke:withNode:for: >>> [:each | >>> (scan >>> processKeystroke: aCharacter asKeystroke >>> withNode: each >>> for: self) >>> ifTrue: [^ self]. >>> nil] in OBColumn>>keystroke:from: >>> OrderedCollection>>reverseDo: >>> OBColumn>>keystroke:from: >>> OBPluggableListMorph(PluggableListMorph)>>modifierKeyPressed: >>> OBPluggableListMorph(PluggableListMorph)>>keyStroke: >>> OBPluggableListMorph(Morph)>>handleKeystroke: >>> KeyboardEvent>>sentTo: >>> OBPluggableListMorph(Morph)>>handleEvent: >>> MorphicEventDispatcher>>dispatchDefault:with: >>> MorphicEventDispatcher>>dispatchEvent:with: >>> OBPluggableListMorph(Morph)>>processEvent:using: >>> OBPluggableListMorph(Morph)>>processEvent: >>> OBPluggableListMorph(PluggableListMorph)>>handleFocusEvent: >>> [ActiveHand := self. >>> ActiveEvent := anEvent. >>> result := focusHolder >>> handleFocusEvent: (anEvent >>> transformedBy: (focusHolder >>> transformedFrom: self))] in HandMorph>>sendFocusEvent:to:clear: >>> [aBlock value] in PasteUpMorph>>becomeActiveDuring: >>> BlockClosure>>on:do: >>> PasteUpMorph>>becomeActiveDuring: >>> HandMorph>>sendFocusEvent:to:clear: >>> HandMorph>>sendEvent:focus:clear: >>> HandMorph>>sendKeyboardEvent: >>> HandMorph>>handleEvent: >>> HandMorph>>processEvents >>> [:h | >>> ActiveHand := h. >>> h processEvents. >>> ActiveHand := nil] in WorldState>>doOneCycleNowFor: >>> Array(SequenceableCollection)>>do: >>> WorldState>>handsDo: >>> WorldState>>doOneCycleNowFor: >>> WorldState>>doOneCycleFor: >>> PasteUpMorph>>doOneCycle >>> [[World doOneCycle. >>> Processor yield. >>> false] whileFalse. >>> nil] in MorphicUIManager>>spawnNewProcess >>> [self value. >>> Processor terminateActive] in BlockClosure>>newProcess >>> >> > >
