• Welcome to Jose's Read Only Forum 2023.

Oxygen Basic 64-bit compiling

Started by Charles Pegge, December 24, 2011, 01:06:23 AM

Previous topic - Next topic

0 Members and 1 Guest are viewing this topic.

Charles Pegge

I have just released Oxygen A038. This version can generate 64bit binaries.

This adds to the three existing modalities thus:

  • compiling 32-bit directly to memory

  • compiling to 32-bit EXE/DLL files with Oxygen.dll dependency

  • compiling to 32-bit EXE/DLL stand-alone files

  • compiling to 64-bit EXE/DLL stand-alone files

In the package, we have accumulated a substantial number of examples for Console, GDI, GDIplus, OpenGL and COM (SAPI).

Oxygen supports Object-Oriented programming and can also dynamically compile functions at run-time.

It is capable of reading both C-style and Basic-style headers

Also provided is a Scintilla-based IDE and a (somewhat brief) CHM manual

It has taken about 4 years to get this far and there is plenty more to do! All welcome to join in :)

Merry Christmas!


Patrice Terrier

Bravo, Charles!

Very impressive work.

Could you just post a small piece of H²O code here, showing us the creation of a window with a common (SDK) message loop,
and how to call an external DLL ?

Patrice Terrier
GDImage (advanced graphic addon)

Petr Schreiber

Great job Charles...

Here is HelloWorld example code (slightly re-idented), picked from the alpha which can be downloaded here:

$ filename "t.exe"
'#include "../../inc/RTL32.inc"
'#include "../../inc/RTL64.inc"
#include "../../inc/MinWin.inc"

#lookahead ' for procedures
if s then
  print s
  goto endprog
end if


    dim cmdline as asciiz ptr, inst as sys
    &cmdline = GetCommandLine
    inst     = GetModuleHandle 0

    WinMain inst,0,cmdline,SW_NORMAL




Function WinMain(sys inst, prevInst, asciiz*cmdline, sys show) as sys

    WndClass wc
    MSG      wm

    sys hwnd, wwd, wht, wtx, wty, tax

    wc.style = CS_HREDRAW or CS_VREDRAW
    wc.lpfnWndProc = &WndProc
    wc.cbClsExtra =0
    wc.cbWndExtra =0   
    wc.hInstance =inst
    wc.hIcon=LoadIcon 0, IDI_APPLICATION
    wc.hCursor=LoadCursor 0,IDC_ARROW
    wc.hbrBackground = GetStockObject WHITE_BRUSH
    wc.lpszMenuName =0
    wc.lpszClassName =@"Demo"

    RegisterClass (&wc)

    Wwd = 320 : Wht = 200
    Tax = GetSystemMetrics SM_CXSCREEN
    Wtx = (Tax - Wwd) /2
    Tax = GetSystemMetrics SM_CYSCREEN
    Wty = (Tax - Wht) /2

    hwnd = CreateWindowEx 0,wc.lpszClassName,"OXYGEN BASIC",WS_OVERLAPPEDWINDOW,Wtx,Wty,Wwd,Wht,0,0,inst,0
    ShowWindow hwnd,SW_SHOW
    UpdateWindow hwnd
    sys bRet
    do while bRet := GetMessage (&wm, 0, 0, 0)
        if bRet = -1 then
          'show an error message
          TranslateMessage &wm
          DispatchMessage &wm
        end if

End Function

dim as rect crect 'for WndProc and TimerProc

function WndProc ( sys hWnd, wMsg, wParam, lparam ) as sys callback

    static as sys hdc
    static as String txt
    static as PaintStruct Paintst

    select wMsg
      case WM_CREATE

      GetClientRect  hWnd,&cRect

      case WM_DESTROY
      PostQuitMessage 0
      case WM_PAINT



      GetClientRect  hWnd,&cRect
      hDC=BeginPaint hWnd,&Paintst
      '0x20 DT_SINGLELINE
      '0x04 DT_VCENTER
      '0x01 DT_CENTER

       SetBkColor   hdc,yellow
       SetTextColor hdc,red
       DrawText hDC,"Hello World!",-1,&cRect,0x25
       EndPaint hWnd,&Paintst
      case WM_KEYDOWN

      Select wParam

    Case 27 : SendMessage hwnd, WM_CLOSE, 0, 0      'ESCAPE

      End Select

      case else
        function=DefWindowProc hWnd,wMsg,wParam,lParam
    end select

end function ' WndProc

AMD Sempron 3400+ | 1GB RAM @ 533MHz | GeForce 6200 / GeForce 9500GT | 32bit Windows XP SP3


Charles Pegge

And here is an elementary example of a 64-bit stand-alone DLL and a program to test it:

  $filename "t64.dll"
  #include "..\..\inc\RTL64.inc"

  print "t64.dll Loaded"

  function HelloA(string s) as string, export
    return "HelloA "+s
  end function

  function HelloW(wstring s) as wstring, export
    return "HelloW "+s
  end function

  $filename "TestHello64.exe"
  #include "..\..\inc\RTL64.inc"

  declare function HelloA lib "t64.dll" (string s) as string
  declare function HelloW lib "t64.dll" (wstring s) as wstring

  print HelloA "World!"
  print HelloW "World!"

These can be found in the package in examples/DLLs


Theo Gottwald

Could it be uses as a supplement for PowerBasic, which has `(at time of this writing)  no x64 version?
How difficult is it to transfer PB Code to OB?
For example a x64 Hook-Dll?

Charles Pegge

Not difficult for windows API programming. o2 has a much smaller function set and different syntax for creating objects and of course none of the specialisations like DDT. But if you need to produce DLLs for 64-bit clients, this is worth a try, and porting back into a latter 64 bit version of PB, should be quite simple, without too many syntax changes.

o2 has a number of features like inner (local) functions and C-style prototypes which you would not find in PB so you have to consider cross-compatibility quite carefully at the outset of a project.


Theo Gottwald

Quoteo2 has a number of features like inner (local) functions

IS the help file up to date?
I did not see anything about objects and such functions in the help file.

Is the assembler and anything included in just that dll or is is separate?

Charles Pegge

The manual is sketchy at this stage, and only covers the basics, but the examples included demonstrate most of the features. One day I hope a comprehensive manual will eventually emerge from Q&A with you guys and the collection of examples :)

o2 is a one piece compiler-assembler-linker, and you can freely mix assembler and basic. This is all coontained within Oxygen.dll. To make use of it as a compiler/executive. To small apps are provided: gxo2 for GUI compiling and exo2 for Console compiling.

the basic Classes look like this:

class testclass

s as string

method get() as string
  method=lcase s
end method

method set(w as string)
end method

end class


dim obj as testclass
obj.set "Hello"
print obj.get

Most entities may have a limited or nested scope, and this includes functions

example of an local/inner function:

function A(v as double) as double
  function cubed(v as double) as double
    return v*v*v
  end function
  return cubed(v)+cubed(v)
end function

print A(2)


Peter Weis

Hello Charles Pegge,
looks good from almost as in Power Basic. I like it! :)
regards Peter

Charles Pegge

Yes it supports a range of coding styles

Take the WndProc prototype for example:


function WndProc(byval hWnd as long, byval uMsg as long, byval wParam as long, byval lParam as long ) as long callback


function WndProc(long hWnd, long uMsg, long wParam, long lParam) as long callback


function WndProc(long hWnd, uMsg, wParam, lParam) as long callback