pharo-project / pharo-launcher

Lets you manage your pharo images and download new ones
https://pharo-project.github.io/pharo-launcher/
MIT License
109 stars 46 forks source link

Unicode characters in ENvironment Variables make the pharo-launcher #620

Open adrian-castravete opened 1 year ago

adrian-castravete commented 1 year ago

Describe the bug Having Unicode characters in any of the environment variables makes the pharo launcher break while Clicking "Show" in the VMs and probably hangs while trying to launch an image.

To Reproduce Steps to reproduce the behavior:

  1. Go to the location where you installed the Pharo Launcher
  2. Click on the launcher file (pharo-launcher)
  3. Update the virtual machines
  4. See error WideString does not understand #tfPointerAddress with a Debug button and an Ignore one.

Expected behavior The Image should open.

Screenshots Error Window: screenshot

Clicking debug I got a hint of the problem: screenshot2

Version information:

Expected development cost I don't really have a good idea. I know about Smalltalk from a long time ago, but I'm at maximum a hobbyist. I have no idea exactly how to fix things. My skills extend to small debugging.

Additional context So as I mentioned and is showed in the screenshots the problem is having

XDG_DOWNLOAD_DIR=/home/fkbm/Descărcări

in the environment. Launching the pharo-launcher with:

XDG_DOWNLOAD_DIR=/home/fkbm/Test/Downloads ./pharo-launcher

A similar error occurs because I also have:

XDG_MUSIC_DIR=/home/fkbm/Muzică

Now relaunching with:

XDG_DOWNLOAD_DIR=/home/fkbm/Test/Downloads XDG_MUSIC_DIR=/home/fkbm/Test/Music ./pharo-launcher

fixes everything, but it's not a normal/nice way of fixing it.

Anyway, for the error showed in the screenshots the debug log is:

THERE_BE_DRAGONS_HERE
Instance of WideString did not understand #tfPointerAddress
29 June 2023 4:42:08.31224 pm

VM: unix - x86_64 - linux-gnu - CoInterpreter * VMMaker-tonel.1 uuid: ad0a8882-d297-0d00-90d3-62ff092bce84 Mar 30 2022
StackToRegisterMappingCogit * VMMaker-tonel.1 uuid: ad0a8882-d297-0d00-90d3-62ff092bce84 Mar 30 2022
v9.0.14 - Commit: 93600e1 - Date: 2022-03-30 16:40:05 +0200

Image: Pharo10.0.0 [Build information: Pharo-10.0.0+build.514.sha.06180671d95a16c446fe24e3fedb0916c1bcb31a (64 Bit)]

WideString(Object)>>doesNotUnderstand: #tfPointerAddress
    Receiver: 'XDG_DOWNLOAD_DIR=/home/fkbm/Descărcări'
    Arguments and temporary variables: 
        aMessage:   tfPointerAddress
        exception:  Instance of WideString did not understand #tfPointerAddress
        resumeValue:    nil
    Receiver's instance variables: 
'XDG_DOWNLOAD_DIR=/home/fkbm/Descărcări'

LibC>>memCopy:to:size:
    Receiver: a LibC
    Arguments and temporary variables: 
        src:    'XDG_DOWNLOAD_DIR=/home/fkbm/Descărcări'
        dest:   @ 16r0120E880
        n:  38
    Receiver's instance variables: 
a LibC

LibC class>>memCopy:to:size:
    Receiver: LibC
    Arguments and temporary variables: 
        from:   'XDG_DOWNLOAD_DIR=/home/fkbm/Descărcări'
        to:     @ 16r0120E880
        size:   38
    Receiver's instance variables: 
        superclass:     FFILibrary
        methodDict:     a MethodDictionary(#currentProcessId->LibC>>#currentProcessId #fget...etc...
        format:     0
        layout:     a FixedLayout
        organization:   a ClassOrganization
        subclasses:     nil
        name:   #LibC
        classPool:  a Dictionary()
        sharedPools:    an OrderedCollection()
        environment:    a SystemDictionary(lots of globals)
        category:   #'UnifiedFFI-Libraries'
        uniqueInstance:     a LibC

[ :aKey :index |
        | string pointer | 
        string := aKey trimmed , '=', (envVariables at: aKey) trimmed. 
        "The +1 is because string must be NULL terminated"
        pointer := ExternalAddress allocate: string size + 1.
        self registerPointer: pointer.
        LibC memCopy: string to: pointer size: string size.
        pointer nbUInt8AtOffset: string size put: 0. "string terminating null char"
        aPointer platformUnsignedLongAt: ((index - 1) * self systemAccessor sizeOfPointer) + 1 put: pointer value
    ] in OSSUnixSubprocess>>collectEnvVariablesPointersInto:
    Receiver: OSSUnixSubprocess(Command: /bin/bash; Pid: nil; Status: Not finished)
    Arguments and temporary variables: 
        aPointer:   @ 16r009DE610
        aKey:   'XDG_DOWNLOAD_DIR'
        index:  4
        string:     'XDG_DOWNLOAD_DIR=/home/fkbm/Descărcări'
        pointer:    @ 16r0120E880
    Receiver's instance variables: 
        command:    '/bin/bash'
        arguments:  #('-c' 'xdg-open "nil"')
        pointers:   a Set(@ 16r0120E880 @ 16r011D3BA0 @ 16r011CEB30 @ 16r009E7380 @ 16r00...etc...
        posixSpawnFileActionsT:     @ 16r011CEB60
        exitStatus:     nil
        envVariables:   a Dictionary('DESKTOP_SESSION_CODE'->'rox-icewm' 'DESKTOP_SESSION...etc...
        stderrStream:   nil
        stdinStream:    nil
        stdoutStream:   nil
        createMissingStandardStreams:   false
        defaultWriteStreamCreationBlock:    [self systemAccessor makeNonBlockingPipe]
        defaultReadStreamCreationBlock:     [self systemAccessor makeBlockingPipe]
        pid:    nil
        retrievedStdout:    a WriteStream
        retrievedStderr:    a WriteStream
        mutexForSigchld:    nil
        shouldContinueWaiting:  nil
        terminateOnShutdown:    false
        workingDirectory:   nil
        waitPidCriticalSemaphore:   a Semaphore()
        encoding:   a ZnUTF8Encoder

Array(SequenceableCollection)>>withIndexDo:
    Receiver: #('XDG_CACHE_HOME' 'XDG_DOCUMENTS_DIR' 'QT_QPA_PLATFORMTHEME' 'XDG_DOWNLOAD_DIR' 'DESKTOP_...etc...
    Arguments and temporary variables: 
        elementAndIndexBlock:   [ :aKey :index |
        | string pointer | 
        string := aKey t...etc...
        index:  4
    Receiver's instance variables: 
#('XDG_CACHE_HOME' 'XDG_DOCUMENTS_DIR' 'QT_QPA_PLATFORMTHEME' 'XDG_DOWNLOAD_DIR' 'DESKTOP_...etc...

OSSUnixSubprocess>>collectEnvVariablesPointersInto:
    Receiver: OSSUnixSubprocess(Command: /bin/bash; Pid: nil; Status: Not finished)
    Arguments and temporary variables: 
        aPointer:   @ 16r009DE610
    Receiver's instance variables: 
        command:    '/bin/bash'
        arguments:  #('-c' 'xdg-open "nil"')
        pointers:   a Set(@ 16r0120E880 @ 16r011D3BA0 @ 16r011CEB30 @ 16r009E7380 @ 16r00...etc...
        posixSpawnFileActionsT:     @ 16r011CEB60
        exitStatus:     nil
        envVariables:   a Dictionary('DESKTOP_SESSION_CODE'->'rox-icewm' 'DESKTOP_SESSION...etc...
        stderrStream:   nil
        stdinStream:    nil
        stdoutStream:   nil
        createMissingStandardStreams:   false
        defaultWriteStreamCreationBlock:    [self systemAccessor makeNonBlockingPipe]
        defaultReadStreamCreationBlock:     [self systemAccessor makeBlockingPipe]
        pid:    nil
        retrievedStdout:    a WriteStream
        retrievedStderr:    a WriteStream
        mutexForSigchld:    nil
        shouldContinueWaiting:  nil
        terminateOnShutdown:    false
        workingDirectory:   nil
        waitPidCriticalSemaphore:   a Semaphore()
        encoding:   a ZnUTF8Encoder

OSSUnixSubprocess>>buildPrimitiveEnvArgument
    Receiver: OSSUnixSubprocess(Command: /bin/bash; Pid: nil; Status: Not finished)
    Arguments and temporary variables: 
        envPointer:     @ 16r009DE610
    Receiver's instance variables: 
        command:    '/bin/bash'
        arguments:  #('-c' 'xdg-open "nil"')
        pointers:   a Set(@ 16r0120E880 @ 16r011D3BA0 @ 16r011CEB30 @ 16r009E7380 @ 16r00...etc...
        posixSpawnFileActionsT:     @ 16r011CEB60
        exitStatus:     nil
        envVariables:   a Dictionary('DESKTOP_SESSION_CODE'->'rox-icewm' 'DESKTOP_SESSION...etc...
        stderrStream:   nil
        stdinStream:    nil
        stdoutStream:   nil
        createMissingStandardStreams:   false
        defaultWriteStreamCreationBlock:    [self systemAccessor makeNonBlockingPipe]
        defaultReadStreamCreationBlock:     [self systemAccessor makeBlockingPipe]
        pid:    nil
        retrievedStdout:    a WriteStream
        retrievedStderr:    a WriteStream
        mutexForSigchld:    nil
        shouldContinueWaiting:  nil
        terminateOnShutdown:    false
        workingDirectory:   nil
        waitPidCriticalSemaphore:   a Semaphore()
        encoding:   a ZnUTF8Encoder

OSSUnixSubprocess>>internalRun
    Receiver: OSSUnixSubprocess(Command: /bin/bash; Pid: nil; Status: Not finished)
    Arguments and temporary variables: 
        pidtPointer:    @ 16r011D3BA0
        returnValue:    nil
    Receiver's instance variables: 
        command:    '/bin/bash'
        arguments:  #('-c' 'xdg-open "nil"')
        pointers:   a Set(@ 16r0120E880 @ 16r011D3BA0 @ 16r011CEB30 @ 16r009E7380 @ 16r00...etc...
        posixSpawnFileActionsT:     @ 16r011CEB60
        exitStatus:     nil
        envVariables:   a Dictionary('DESKTOP_SESSION_CODE'->'rox-icewm' 'DESKTOP_SESSION...etc...
        stderrStream:   nil
        stdinStream:    nil
        stdoutStream:   nil
        createMissingStandardStreams:   false
        defaultWriteStreamCreationBlock:    [self systemAccessor makeNonBlockingPipe]
        defaultReadStreamCreationBlock:     [self systemAccessor makeBlockingPipe]
        pid:    nil
        retrievedStdout:    a WriteStream
        retrievedStderr:    a WriteStream
        mutexForSigchld:    nil
        shouldContinueWaiting:  nil
        terminateOnShutdown:    false
        workingDirectory:   nil
        waitPidCriticalSemaphore:   a Semaphore()
        encoding:   a ZnUTF8Encoder

[ self internalRun ] in OSSUnixSubprocess>>run
    Receiver: OSSUnixSubprocess(Command: /bin/bash; Pid: nil; Status: Not finished)
    Arguments and temporary variables: 
x
    Receiver's instance variables: 
        command:    '/bin/bash'
        arguments:  #('-c' 'xdg-open "nil"')
        pointers:   a Set(@ 16r0120E880 @ 16r011D3BA0 @ 16r011CEB30 @ 16r009E7380 @ 16r00...etc...
        posixSpawnFileActionsT:     @ 16r011CEB60
        exitStatus:     nil
        envVariables:   a Dictionary('DESKTOP_SESSION_CODE'->'rox-icewm' 'DESKTOP_SESSION...etc...
        stderrStream:   nil
        stdinStream:    nil
        stdoutStream:   nil
        createMissingStandardStreams:   false
        defaultWriteStreamCreationBlock:    [self systemAccessor makeNonBlockingPipe]
        defaultReadStreamCreationBlock:     [self systemAccessor makeBlockingPipe]
        pid:    nil
        retrievedStdout:    a WriteStream
        retrievedStderr:    a WriteStream
        mutexForSigchld:    nil
        shouldContinueWaiting:  nil
        terminateOnShutdown:    false
        workingDirectory:   nil
        waitPidCriticalSemaphore:   a Semaphore()
        encoding:   a ZnUTF8Encoder

FullBlockClosure(BlockClosure)>>ensure:
    Receiver: [ self internalRun ]
    Arguments and temporary variables: 
        aBlock:     [ 
        self cleanResources.
    ]
        complete:   nil
        returnValue:    nil
    Receiver's instance variables: 
        outerContext:   OSSUnixSubprocess>>run
        startpc:    a CompiledBlock: [ self internalRun ]
        numArgs:    0
        receiver:   OSSUnixSubprocess(Command: /bin/bash; Pid: nil; Status: Not finished)...etc...

OSSUnixSubprocess>>run
    Receiver: OSSUnixSubprocess(Command: /bin/bash; Pid: nil; Status: Not finished)
    Arguments and temporary variables: 
x
    Receiver's instance variables: 
        command:    '/bin/bash'
        arguments:  #('-c' 'xdg-open "nil"')
        pointers:   a Set(@ 16r0120E880 @ 16r011D3BA0 @ 16r011CEB30 @ 16r009E7380 @ 16r00...etc...
        posixSpawnFileActionsT:     @ 16r011CEB60
        exitStatus:     nil
        envVariables:   a Dictionary('DESKTOP_SESSION_CODE'->'rox-icewm' 'DESKTOP_SESSION...etc...
        stderrStream:   nil
        stdinStream:    nil
        stdoutStream:   nil
        createMissingStandardStreams:   false
        defaultWriteStreamCreationBlock:    [self systemAccessor makeNonBlockingPipe]
        defaultReadStreamCreationBlock:     [self systemAccessor makeBlockingPipe]
        pid:    nil
        retrievedStdout:    a WriteStream
        retrievedStderr:    a WriteStream
        mutexForSigchld:    nil
        shouldContinueWaiting:  nil
        terminateOnShutdown:    false
        workingDirectory:   nil
        waitPidCriticalSemaphore:   a Semaphore()
        encoding:   a ZnUTF8Encoder

PhLProcessWrapper>>runUnwatch
    Receiver: a PhLProcessWrapper
    Arguments and temporary variables: 
x
    Receiver's instance variables: 
        process:    OSSUnixSubprocess(Command: /bin/bash; Pid: nil; Status: Not finished)
        arguments:  an OrderedCollection('xdg-open "nil"')
        command:    nil
        workingDirectory:   nil
        isShellCommand:     true
        useLoginShell:  false

PhLFileBrowser>>visitUnix:
    Receiver: a PhLFileBrowser
    Arguments and temporary variables: 
        aPlatform:  an Unix64Platform
    Receiver's instance variables: 
        process:    nil
        vmPath:     nil
        launchInALoginShell:    nil
        imageFile:  nil
        usePharoSettings:   nil
        path:   nil

PhLFileBrowser(OSPlatformVisitor)>>visitUnix64:
    Receiver: a PhLFileBrowser
    Arguments and temporary variables: 
        aPlatform:  an Unix64Platform
    Receiver's instance variables: 
        process:    nil
        vmPath:     nil
        launchInALoginShell:    nil
        imageFile:  nil
        usePharoSettings:   nil
        path:   nil

Unix64Platform>>accept:
    Receiver: an Unix64Platform
    Arguments and temporary variables: 
        aVisitor:   a PhLFileBrowser
    Receiver's instance variables: 
an Unix64Platform

PhLFileBrowser(OSPlatformVisitor)>>visit
    Receiver: a PhLFileBrowser
    Arguments and temporary variables: 
x
    Receiver's instance variables: 
        process:    nil
        vmPath:     nil
        launchInALoginShell:    nil
        imageFile:  nil
        usePharoSettings:   nil
        path:   nil

PhLFileBrowser>>open
    Receiver: a PhLFileBrowser
    Arguments and temporary variables: 
x
    Receiver's instance variables: 
        process:    nil
        vmPath:     nil
        launchInALoginShell:    nil
        imageFile:  nil
        usePharoSettings:   nil
        path:   nil

PhLFileBrowser class>>openOn:
    Receiver: PhLFileBrowser
    Arguments and temporary variables: 
        aFileReferenceOrPathString:     File @ /home/fkbm/Pharo/vms/100-x64
    Receiver's instance variables: 
        superclass:     OSPlatformVisitor
        methodDict:     a MethodDictionary(#open->PhLFileBrowser>>#open #path:->PhLFileBrow...etc...
        format:     65542
        layout:     a FixedLayout
        organization:   a ClassOrganization
        subclasses:     nil
        name:   #PhLFileBrowser
        classPool:  a Dictionary()
        sharedPools:    an OrderedCollection()
        environment:    a SystemDictionary(lots of globals)
        category:   #'PharoLauncher-Core-Model'

PhLVirtualMachine>>showInFolder
    Receiver: a PhLVirtualMachine(100-x64)
    Arguments and temporary variables: 
x
    Receiver's instance variables: 
        executableRef:  nil
        vmBinaryRef:    nil
        name:   nil
        manager:    a PhLVirtualMachineManager
        flavour:    ''
        id:     '100-x64'
        blessing:   'stable'
        arch:   '64'

PhLShowVmInFolderCommand>>execute
    Receiver: a PhLShowVmInFolderCommand
    Arguments and temporary variables: 
        vms:    an OrderedCollection(a PhLVirtualMachine(100-x64))
    Receiver's instance variables: 
        context:    a PhLVMPresenter
        basicName:  'Show'
        basicDescription:   'Open your OS''s file browser on the selected VM directory.'

SpCommand(CmCommandDecorator)>>execute
    Receiver: a SpCommand(Show)
    Arguments and temporary variables: 
x
    Receiver's instance variables: 
        decoratedCommand:   a PhLShowVmInFolderCommand
        iconProvider:   a ThemeIcons(idea11)
        iconName:   #openIcon
        shortcutKey:    Meta + O
        displayStrategy:    a CmUIDisableWhenCantBeRun
        positionStrategy:   a CmUILeftPositionStrategy
        buildPresenterBlock:    [ :specCommand | 
            aButtonClass new
                label: specComma...etc...
        presenter:  a SpToolbarButtonPresenter

[ specCommand execute ] in [ :specCommand | 
            aButtonClass new
                label: specCommand name;
                help: specCommand description;
                in: [ :button | 
                    specCommand hasIcon
                        ifTrue: [ button icon: specCommand icon ] ];
                action: [ specCommand execute ];
                yourself ] in SpCommand>>configureAsButtonOfClass:
    Receiver: a SpCommand(Show)
    Arguments and temporary variables: 
        aButtonClass:   nil
        specCommand:    a SpCommand(Show)
    Receiver's instance variables: 
        decoratedCommand:   a PhLShowVmInFolderCommand
        iconProvider:   a ThemeIcons(idea11)
        iconName:   #openIcon
        shortcutKey:    Meta + O
        displayStrategy:    a CmUIDisableWhenCantBeRun
        positionStrategy:   a CmUILeftPositionStrategy
        buildPresenterBlock:    [ :specCommand | 
            aButtonClass new
                label: specComma...etc...
        presenter:  a SpToolbarButtonPresenter

FullBlockClosure(BlockClosure)>>cull:
    Receiver: [ specCommand execute ]
    Arguments and temporary variables: 
        anArg:  a SpToolbarButtonPresenter
    Receiver's instance variables: 
        outerContext:   [ :specCommand | 
            aButtonClass new
                label: specCommand name...etc...
        startpc:    a CompiledBlock: [ specCommand execute ]
        numArgs:    0
        receiver:   a SpCommand(Show)

SpMorphicToolbarButtonAdapter>>execute
    Receiver: a SpMorphicToolbarButtonAdapter
    Arguments and temporary variables: 
x
    Receiver's instance variables: 
        dependents:     a DependentsArray(a SpToolbarButtonMorph(410691840))
        announcer:  nil
        model:  a SpToolbarButtonPresenter
        widget:     a SpToolbarButtonMorph(410691840)
        selector:   nil
        owner:  a SpToolbarButtonPresenter
        unsubscribed:   false

SpToolbarButtonMorph(PluggableButtonMorph)>>performAction:
    Receiver: a SpToolbarButtonMorph(410691840)
    Arguments and temporary variables: 
        event:  [(214@313) mouseUp 99444 nil]
    Receiver's instance variables: 
        bounds:     (196.0@297.0) corner: (241.0@331.0)
        owner:  a Morph(113793536)
        submorphs:  an Array(an AlignmentMorph(660598528))
        fullBounds:     nil
        color:  (Color r: 0.2903225806451613 g: 0.2883675464320626 b: 0.2883675464320626...etc...
        extension:  a MorphExtension (709474304) [balloonText]  [other:  (presenter -> a...etc...
        borderWidth:    0
        borderColor:    #simple
        model:  a SpMorphicToolbarButtonAdapter
        label:  'Show'
        icon:   Form(16x16x32)
        getIconSelector:    #icon
        getStateSelector:   #state
        actionSelector:     #execute
        font:   a LogicalFont
 familyName: 'Source Sans Pro'
 emphasis: nil
 pointSize: 7...etc...
        getLabelSelector:   #label
        getMenuSelector:    nil
        shortcutCharacter:  nil
        askBeforeChanging:  false
        triggerOnMouseDown:     false
        offColor:   nil
        onColor:    nil
        feedbackColor:  nil
        showSelectionFeedback:  false
        allButtons:     nil
        arguments:  #()
        argumentsProvider:  nil
        argumentsSelector:  nil
        enabled:    true
        actionBlock:    nil
        getColorSelector:   nil
        getEnabledSelector:     nil
        getFontSelector:    nil
        labelMorph:     a LabelMorph(233016320)'Show'
        iconMorph:  an ImageMorph(642061056)
        iconPosition:   #top
        lastState:  false
        badgeFont:  nil
        badgeSelector:  #badge

[:m |
        (m containsPoint: evt cursorPoint) ifTrue: [m enabled ifTrue: [ m performAction: evt ]]] in SpToolbarButtonMorph(PluggableButtonMorph)>>mouseUp:
    Receiver: a SpToolbarButtonMorph(410691840)
    Arguments and temporary variables: 
        evt:    [(214@313) mouseUp 99444 nil]
        all:    an Array(a SpToolbarButtonMorph(43449600) a SpToolbarButtonMorph(410691840...etc...
        m:  a SpToolbarButtonMorph(410691840)
    Receiver's instance variables: 
        bounds:     (196.0@297.0) corner: (241.0@331.0)
        owner:  a Morph(113793536)
        submorphs:  an Array(an AlignmentMorph(660598528))
        fullBounds:     nil
        color:  (Color r: 0.2903225806451613 g: 0.2883675464320626 b: 0.2883675464320626...etc...
        extension:  a MorphExtension (709474304) [balloonText]  [other:  (presenter -> a...etc...
        borderWidth:    0
        borderColor:    #simple
        model:  a SpMorphicToolbarButtonAdapter
        label:  'Show'
        icon:   Form(16x16x32)
        getIconSelector:    #icon
        getStateSelector:   #state
        actionSelector:     #execute
        font:   a LogicalFont
 familyName: 'Source Sans Pro'
 emphasis: nil
 pointSize: 7...etc...
        getLabelSelector:   #label
        getMenuSelector:    nil
        shortcutCharacter:  nil
        askBeforeChanging:  false
        triggerOnMouseDown:     false
        offColor:   nil
        onColor:    nil
        feedbackColor:  nil
        showSelectionFeedback:  false
        allButtons:     nil
        arguments:  #()
        argumentsProvider:  nil
        argumentsSelector:  nil
        enabled:    true
        actionBlock:    nil
        getColorSelector:   nil
        getEnabledSelector:     nil
        getFontSelector:    nil
        labelMorph:     a LabelMorph(233016320)'Show'
        iconMorph:  an ImageMorph(642061056)
        iconPosition:   #top
        lastState:  false
        badgeFont:  nil
        badgeSelector:  #badge

Array(SequenceableCollection)>>do:
    Receiver: an Array(a SpToolbarButtonMorph(43449600) a SpToolbarButtonMorph(410691840) a SpToolbarBut...etc...
    Arguments and temporary variables: 
        aBlock:     [:m |
        (m containsPoint: evt cursorPoint) ifTrue: [m enabled ifTrue: [...etc...
        index:  2
    Receiver's instance variables: 
an Array(a SpToolbarButtonMorph(43449600) a SpToolbarButtonMorph(410691840) a SpToolbarBut...etc...

SpToolbarButtonMorph(PluggableButtonMorph)>>mouseUp:
    Receiver: a SpToolbarButtonMorph(410691840)
    Arguments and temporary variables: 
        evt:    [(214@313) mouseUp 99444 nil]
        all:    an Array(a SpToolbarButtonMorph(43449600) a SpToolbarButtonMorph(410691840...etc...
    Receiver's instance variables: 
        bounds:     (196.0@297.0) corner: (241.0@331.0)
        owner:  a Morph(113793536)
        submorphs:  an Array(an AlignmentMorph(660598528))
        fullBounds:     nil
        color:  (Color r: 0.2903225806451613 g: 0.2883675464320626 b: 0.2883675464320626...etc...
        extension:  a MorphExtension (709474304) [balloonText]  [other:  (presenter -> a...etc...
        borderWidth:    0
        borderColor:    #simple
        model:  a SpMorphicToolbarButtonAdapter
        label:  'Show'
        icon:   Form(16x16x32)
        getIconSelector:    #icon
        getStateSelector:   #state
        actionSelector:     #execute
        font:   a LogicalFont
 familyName: 'Source Sans Pro'
 emphasis: nil
 pointSize: 7...etc...
        getLabelSelector:   #label
        getMenuSelector:    nil
        shortcutCharacter:  nil
        askBeforeChanging:  false
        triggerOnMouseDown:     false
        offColor:   nil
        onColor:    nil
        feedbackColor:  nil
        showSelectionFeedback:  false
        allButtons:     nil
        arguments:  #()
        argumentsProvider:  nil
        argumentsSelector:  nil
        enabled:    true
        actionBlock:    nil
        getColorSelector:   nil
        getEnabledSelector:     nil
        getFontSelector:    nil
        labelMorph:     a LabelMorph(233016320)'Show'
        iconMorph:  an ImageMorph(642061056)
        iconPosition:   #top
        lastState:  false
        badgeFont:  nil
        badgeSelector:  #badge

SpToolbarButtonMorph(Morph)>>handleMouseUp:
    Receiver: a SpToolbarButtonMorph(410691840)
    Arguments and temporary variables: 
        anEvent:    [(214@313) mouseUp 99444 nil]
        result:     nil
    Receiver's instance variables: 
        bounds:     (196.0@297.0) corner: (241.0@331.0)
        owner:  a Morph(113793536)
        submorphs:  an Array(an AlignmentMorph(660598528))
        fullBounds:     nil
        color:  (Color r: 0.2903225806451613 g: 0.2883675464320626 b: 0.2883675464320626...etc...
        extension:  a MorphExtension (709474304) [balloonText]  [other:  (presenter -> a...etc...
        borderWidth:    0
        borderColor:    #simple
        model:  a SpMorphicToolbarButtonAdapter
        label:  'Show'
        icon:   Form(16x16x32)
        getIconSelector:    #icon
        getStateSelector:   #state
        actionSelector:     #execute
        font:   a LogicalFont
 familyName: 'Source Sans Pro'
 emphasis: nil
 pointSize: 7...etc...
        getLabelSelector:   #label
        getMenuSelector:    nil
        shortcutCharacter:  nil
        askBeforeChanging:  false
        triggerOnMouseDown:     false
        offColor:   nil
        onColor:    nil
        feedbackColor:  nil
        showSelectionFeedback:  false
        allButtons:     nil
        arguments:  #()
        argumentsProvider:  nil
        argumentsSelector:  nil
        enabled:    true
        actionBlock:    nil
        getColorSelector:   nil
        getEnabledSelector:     nil
        getFontSelector:    nil
        labelMorph:     a LabelMorph(233016320)'Show'
        iconMorph:  an ImageMorph(642061056)
        iconPosition:   #top
        lastState:  false
        badgeFont:  nil
        badgeSelector:  #badge

MouseButtonEvent>>sentTo:
    Receiver: [(214@313) mouseUp 99444 nil]
    Arguments and temporary variables: 
        anObject:   a SpToolbarButtonMorph(410691840)
    Receiver's instance variables: 
        timeStamp:  99444
        source:     a HandMorph(602983936)
        windowIndex:    nil
        type:   #mouseUp
        buttons:    0
        position:   (214@313)
        handler:    nil
        wasHandled:     true
        whichButton:    4

SpToolbarButtonMorph(Morph)>>handleEvent:
    Receiver: a SpToolbarButtonMorph(410691840)
    Arguments and temporary variables: 
        anEvent:    [(214@313) mouseUp 99444 nil]
    Receiver's instance variables: 
        bounds:     (196.0@297.0) corner: (241.0@331.0)
        owner:  a Morph(113793536)
        submorphs:  an Array(an AlignmentMorph(660598528))
        fullBounds:     nil
        color:  (Color r: 0.2903225806451613 g: 0.2883675464320626 b: 0.2883675464320626...etc...
        extension:  a MorphExtension (709474304) [balloonText]  [other:  (presenter -> a...etc...
        borderWidth:    0
        borderColor:    #simple
        model:  a SpMorphicToolbarButtonAdapter
        label:  'Show'
        icon:   Form(16x16x32)
        getIconSelector:    #icon
        getStateSelector:   #state
        actionSelector:     #execute
        font:   a LogicalFont
 familyName: 'Source Sans Pro'
 emphasis: nil
 pointSize: 7...etc...
        getLabelSelector:   #label
        getMenuSelector:    nil
        shortcutCharacter:  nil
        askBeforeChanging:  false
        triggerOnMouseDown:     false
        offColor:   nil
        onColor:    nil
        feedbackColor:  nil
        showSelectionFeedback:  false
        allButtons:     nil
        arguments:  #()
        argumentsProvider:  nil
        argumentsSelector:  nil
        enabled:    true
        actionBlock:    nil
        getColorSelector:   nil
        getEnabledSelector:     nil
        getFontSelector:    nil
        labelMorph:     a LabelMorph(233016320)'Show'
        iconMorph:  an ImageMorph(642061056)
        iconPosition:   #top
        lastState:  false
        badgeFont:  nil
        badgeSelector:  #badge

SpToolbarButtonMorph(Morph)>>handleFocusEvent:
    Receiver: a SpToolbarButtonMorph(410691840)
    Arguments and temporary variables: 
        anEvent:    [(214@313) mouseUp 99444 nil]
    Receiver's instance variables: 
        bounds:     (196.0@297.0) corner: (241.0@331.0)
        owner:  a Morph(113793536)
        submorphs:  an Array(an AlignmentMorph(660598528))
        fullBounds:     nil
        color:  (Color r: 0.2903225806451613 g: 0.2883675464320626 b: 0.2883675464320626...etc...
        extension:  a MorphExtension (709474304) [balloonText]  [other:  (presenter -> a...etc...
        borderWidth:    0
        borderColor:    #simple
        model:  a SpMorphicToolbarButtonAdapter
        label:  'Show'
        icon:   Form(16x16x32)
        getIconSelector:    #icon
        getStateSelector:   #state
        actionSelector:     #execute
        font:   a LogicalFont
 familyName: 'Source Sans Pro'
 emphasis: nil
 pointSize: 7...etc...
        getLabelSelector:   #label
        getMenuSelector:    nil
        shortcutCharacter:  nil
        askBeforeChanging:  false
        triggerOnMouseDown:     false
        offColor:   nil
        onColor:    nil
        feedbackColor:  nil
        showSelectionFeedback:  false
        allButtons:     nil
        arguments:  #()
        argumentsProvider:  nil
        argumentsSelector:  nil
        enabled:    true
        actionBlock:    nil
        getColorSelector:   nil
        getEnabledSelector:     nil
        getFontSelector:    nil
        labelMorph:     a LabelMorph(233016320)'Show'
        iconMorph:  an ImageMorph(642061056)
        iconPosition:   #top
        lastState:  false
        badgeFont:  nil
        badgeSelector:  #badge

[
        result := focusHolder handleFocusEvent: transformedEvent.
    ] in HandMorph>>sendFocusEvent:to:clear:
    Receiver: a HandMorph(602983936)
    Arguments and temporary variables: 
        anEvent:    [(214@313) mouseUp 99444 nil]
        focusHolder:    a SpToolbarButtonMorph(410691840)
        aBlock:     [self mouseFocus: nil]
        w:  a WorldMorph(757016832) [world]
        transformedEvent:   [(214@313) mouseUp 99444 nil]
        result:     nil
    Receiver's instance variables: 
        bounds:     (214@313) corner: (230@329)
        owner:  a WorldMorph(757016832) [world]
        submorphs:  #()
        fullBounds:     (214@313) corner: (230@329)
        color:  Color blue
        extension:  a MorphExtension (369664768)
        mouseFocus:     nil
        keyboardFocus:  a SpFTTableMorph(338146048)
        eventListeners:     nil
        mouseListeners:     nil
        mouseClickState:    nil
        mouseOverHandler:   a MouseOverHandler
        lastMouseEvent:     [(214@313) mouseUp 99444 nil]
        targetOffset:   (18.0@16.0)
        damageRecorder:     a DamageRecorder
        cacheCanvas:    nil
        cachedCanvasHasHoles:   false
        temporaryCursor:    nil
        temporaryCursorOffset:  nil
        hardwareCursor:     nil
        hasChanged:     true
        savedPatch:     nil
        lastEventBuffer:    #(1 0 0 0 0 0 nil nil)
        captureBlock:   nil
        recentModifiers:    0
        pendingEventQueue:  WaitfreeQueue with 0 items
        supressNextKeyPress:    false

FullBlockClosure(BlockClosure)>>on:do:
    Receiver: [
        result := focusHolder handleFocusEvent: transformedEvent.
    ]
    Arguments and temporary variables: 
        exception:  Error
        handlerAction:  [ :ex | 
            ActiveWorld := priorWorld.
            ex pass ]
    Receiver's instance variables: 
        outerContext:   HandMorph>>sendFocusEvent:to:clear:
        startpc:    a CompiledBlock: [
        result := focusHolder handleFocusEvent: transform...etc...
        numArgs:    0
        receiver:   a HandMorph(602983936)

WorldMorph>>becomeActiveDuring:
    Receiver: a WorldMorph(757016832) [world]
    Arguments and temporary variables: 
        aBlock:     [
        result := focusHolder handleFocusEvent: transformedEvent.
    ]
        priorWorld:     a WorldMorph(757016832) [world]
    Receiver's instance variables: 
        bounds:     (0@0) corner: (952@1053)
        owner:  nil
        submorphs:  an Array(a SpWindow(267380480) named: Locally available Virtual Mach...etc...
        fullBounds:     (0@0) corner: (952@1053)
        color:  (Color r: 0.1300097751710655 g: 0.1300097751710655 b: 0.1300097751710655...etc...
        extension:  a MorphExtension (1003056896) [other:  (dragEnabled -> true) (dropEn...etc...
        borderWidth:    4
        borderColor:    (Color r: 0.1300097751710655 g: 0.1300097751710655 b: 0.1300097751...etc...
        backgroundMorph:    nil
        worldState:     a WorldState
        griddingOn:     nil

HandMorph>>sendFocusEvent:to:clear:
    Receiver: a HandMorph(602983936)
    Arguments and temporary variables: 
        result:     nil
        anEvent:    [(214@313) mouseUp 99444 nil]
        focusHolder:    a SpToolbarButtonMorph(410691840)
        aBlock:     [self mouseFocus: nil]
        w:  a WorldMorph(757016832) [world]
        transformedEvent:   [(214@313) mouseUp 99444 nil]
    Receiver's instance variables: 
        bounds:     (214@313) corner: (230@329)
        owner:  a WorldMorph(757016832) [world]
        submorphs:  #()
        fullBounds:     (214@313) corner: (230@329)
        color:  Color blue
        extension:  a MorphExtension (369664768)
        mouseFocus:     nil
        keyboardFocus:  a SpFTTableMorph(338146048)
        eventListeners:     nil
        mouseListeners:     nil
        mouseClickState:    nil
        mouseOverHandler:   a MouseOverHandler
        lastMouseEvent:     [(214@313) mouseUp 99444 nil]
        targetOffset:   (18.0@16.0)
        damageRecorder:     a DamageRecorder
        cacheCanvas:    nil
        cachedCanvasHasHoles:   false
        temporaryCursor:    nil
        temporaryCursorOffset:  nil
        hardwareCursor:     nil
        hasChanged:     true
        savedPatch:     nil
        lastEventBuffer:    #(1 0 0 0 0 0 nil nil)
        captureBlock:   nil
        recentModifiers:    0
        pendingEventQueue:  WaitfreeQueue with 0 items
        supressNextKeyPress:    false

HandMorph>>sendEvent:focus:clear:
    Receiver: a HandMorph(602983936)
    Arguments and temporary variables: 
        anEvent:    [(214@313) mouseUp 99444 nil]
        focusHolder:    a SpToolbarButtonMorph(410691840)
        aBlock:     [self mouseFocus: nil]
        result:     nil
    Receiver's instance variables: 
        bounds:     (214@313) corner: (230@329)
        owner:  a WorldMorph(757016832) [world]
        submorphs:  #()
        fullBounds:     (214@313) corner: (230@329)
        color:  Color blue
        extension:  a MorphExtension (369664768)
        mouseFocus:     nil
        keyboardFocus:  a SpFTTableMorph(338146048)
        eventListeners:     nil
        mouseListeners:     nil
        mouseClickState:    nil
        mouseOverHandler:   a MouseOverHandler
        lastMouseEvent:     [(214@313) mouseUp 99444 nil]
        targetOffset:   (18.0@16.0)
        damageRecorder:     a DamageRecorder
        cacheCanvas:    nil
        cachedCanvasHasHoles:   false
        temporaryCursor:    nil
        temporaryCursorOffset:  nil
        hardwareCursor:     nil
        hasChanged:     true
        savedPatch:     nil
        lastEventBuffer:    #(1 0 0 0 0 0 nil nil)
        captureBlock:   nil
        recentModifiers:    0
        pendingEventQueue:  WaitfreeQueue with 0 items
        supressNextKeyPress:    false

HandMorph>>sendMouseEvent:
    Receiver: a HandMorph(602983936)
    Arguments and temporary variables: 
        anEvent:    [(214@313) mouseUp 99444 nil]
    Receiver's instance variables: 
        bounds:     (214@313) corner: (230@329)
        owner:  a WorldMorph(757016832) [world]
        submorphs:  #()
        fullBounds:     (214@313) corner: (230@329)
        color:  Color blue
        extension:  a MorphExtension (369664768)
        mouseFocus:     nil
        keyboardFocus:  a SpFTTableMorph(338146048)
        eventListeners:     nil
        mouseListeners:     nil
        mouseClickState:    nil
        mouseOverHandler:   a MouseOverHandler
        lastMouseEvent:     [(214@313) mouseUp 99444 nil]
        targetOffset:   (18.0@16.0)
        damageRecorder:     a DamageRecorder
        cacheCanvas:    nil
        cachedCanvasHasHoles:   false
        temporaryCursor:    nil
        temporaryCursorOffset:  nil
        hardwareCursor:     nil
        hasChanged:     true
        savedPatch:     nil
        lastEventBuffer:    #(1 0 0 0 0 0 nil nil)
        captureBlock:   nil
        recentModifiers:    0
        pendingEventQueue:  WaitfreeQueue with 0 items
        supressNextKeyPress:    false

HandMorph>>handleEvent:
    Receiver: a HandMorph(602983936)
    Arguments and temporary variables: 
        anEvent:    [(214@313) mouseUp 99444 nil]
        evt:    [(214@313) mouseUp 99444 nil]
    Receiver's instance variables: 
        bounds:     (214@313) corner: (230@329)
        owner:  a WorldMorph(757016832) [world]
        submorphs:  #()
        fullBounds:     (214@313) corner: (230@329)
        color:  Color blue
        extension:  a MorphExtension (369664768)
        mouseFocus:     nil
        keyboardFocus:  a SpFTTableMorph(338146048)
        eventListeners:     nil
        mouseListeners:     nil
        mouseClickState:    nil
        mouseOverHandler:   a MouseOverHandler
        lastMouseEvent:     [(214@313) mouseUp 99444 nil]
        targetOffset:   (18.0@16.0)
        damageRecorder:     a DamageRecorder
        cacheCanvas:    nil
        cachedCanvasHasHoles:   false
        temporaryCursor:    nil
        temporaryCursorOffset:  nil
        hardwareCursor:     nil
        hasChanged:     true
        savedPatch:     nil
        lastEventBuffer:    #(1 0 0 0 0 0 nil nil)
        captureBlock:   nil
        recentModifiers:    0
        pendingEventQueue:  WaitfreeQueue with 0 items
        supressNextKeyPress:    false

--- The full stack ---
WideString(Object)>>doesNotUnderstand: #tfPointerAddress
LibC>>memCopy:to:size:
LibC class>>memCopy:to:size:
[ :aKey :index |
        | string pointer | 
        string := aKey trimmed , '=', (envVariables at: aKey) trimmed. 
        "The +1 is because string must be NULL terminated"
        pointer := ExternalAddress allocate: string size + 1.
        self registerPointer: pointer.
        LibC memCopy: string to: pointer size: string size.
        pointer nbUInt8AtOffset: string size put: 0. "string terminating null char"
        aPointer platformUnsignedLongAt: ((index - 1) * self systemAccessor sizeOfPointer) + 1 put: pointer value
    ] in OSSUnixSubprocess>>collectEnvVariablesPointersInto:
Array(SequenceableCollection)>>withIndexDo:
OSSUnixSubprocess>>collectEnvVariablesPointersInto:
OSSUnixSubprocess>>buildPrimitiveEnvArgument
OSSUnixSubprocess>>internalRun
[ self internalRun ] in OSSUnixSubprocess>>run
FullBlockClosure(BlockClosure)>>ensure:
OSSUnixSubprocess>>run
PhLProcessWrapper>>runUnwatch
PhLFileBrowser>>visitUnix:
PhLFileBrowser(OSPlatformVisitor)>>visitUnix64:
Unix64Platform>>accept:
PhLFileBrowser(OSPlatformVisitor)>>visit
PhLFileBrowser>>open
PhLFileBrowser class>>openOn:
PhLVirtualMachine>>showInFolder
PhLShowVmInFolderCommand>>execute
SpCommand(CmCommandDecorator)>>execute
[ specCommand execute ] in [ :specCommand | 
            aButtonClass new
                label: specCommand name;
                help: specCommand description;
                in: [ :button | 
                    specCommand hasIcon
                        ifTrue: [ button icon: specCommand icon ] ];
                action: [ specCommand execute ];
                yourself ] in SpCommand>>configureAsButtonOfClass:
FullBlockClosure(BlockClosure)>>cull:
SpMorphicToolbarButtonAdapter>>execute
SpToolbarButtonMorph(PluggableButtonMorph)>>performAction:
[:m |
        (m containsPoint: evt cursorPoint) ifTrue: [m enabled ifTrue: [ m performAction: evt ]]] in SpToolbarButtonMorph(PluggableButtonMorph)>>mouseUp:
Array(SequenceableCollection)>>do:
SpToolbarButtonMorph(PluggableButtonMorph)>>mouseUp:
SpToolbarButtonMorph(Morph)>>handleMouseUp:
MouseButtonEvent>>sentTo:
SpToolbarButtonMorph(Morph)>>handleEvent:
SpToolbarButtonMorph(Morph)>>handleFocusEvent:
[
        result := focusHolder handleFocusEvent: transformedEvent.
    ] in HandMorph>>sendFocusEvent:to:clear:
FullBlockClosure(BlockClosure)>>on:do:
WorldMorph>>becomeActiveDuring:
HandMorph>>sendFocusEvent:to:clear:
HandMorph>>sendEvent:focus:clear:
HandMorph>>sendMouseEvent:
HandMorph>>handleEvent:
 - - - - - - - - - - - - - - -  
            - - - - - - - - - - - - - - - - - -
[
        (morphicWorld activeHand isNotNil and: [ anEvent hand isNotNil ]) ifTrue: [
            morphicWorld activeHand handleEvent: anEvent
        ]
    ] in OSWindowMorphicEventHandler>>dispatchMorphicEvent:
WorldState>>runStepMethodsIn:
WorldMorph>>runStepMethods
WorldState>>doOneCycleFor:
WorldMorph>>doOneCycleNow
WorldMorph>>doOneCycle
[ 
        | extraWorldsToDraw |
        extraWorldsToDraw := ExtraWorldListMutex critical: [ 
                                 self extraWorldList ].
        extraWorldsToDraw do: [ :world | world doOneCycle ].

        (self currentWorld isNotNil and: [ 
             (extraWorldsToDraw includes: self currentWorld) not ]) ifTrue: [ 
            self currentWorld doOneCycle ] ] in WorldMorph class>>doOneCycle
FullBlockClosure(BlockClosure)>>ensure:
WorldState class>>doDrawCycleWith:
WorldMorph class>>doOneCycle
MorphicRenderLoop>>doOneCycle
MorphicRenderLoop>>doOneCycleWhile:
[
        MorphicRenderLoop new doOneCycleWhile: [ true ]
    ] in MorphicUIManager>>spawnNewProcess
[self value.
            "IMPORTANT: Do not step over next line of code. See method comments for details"
            Processor terminateRealActive] in FullBlockClosure(BlockClosure)>>newProcess
terpon commented 1 week ago

The issue still happens with pharo-launcher-linux-3.2-64. It was reported on the pharo discord.

I could reproduce it with:

 export AAA=çōî
 ./pharo-launcher-ui 

Looks like OSSubprocess package is copying environment variables. FFI translates some char* to ByteString and others to WideString. The reverse process (in the FFI memcpy method) is not handled for WideString instances.