compiler: add support for $if x32, x64, big_endian, little_endian
parent
751a89ccc8
commit
e577b40743
|
@ -12,6 +12,22 @@ c_headers = '
|
||||||
#include <stdarg.h> // for va_list
|
#include <stdarg.h> // for va_list
|
||||||
#include <string.h> // memcpy
|
#include <string.h> // memcpy
|
||||||
|
|
||||||
|
#if INTPTR_MAX == INT32_MAX
|
||||||
|
#define TARGET_IS_32BIT 1
|
||||||
|
#elif INTPTR_MAX == INT64_MAX
|
||||||
|
#define TARGET_IS_64BIT 1
|
||||||
|
#else
|
||||||
|
#error "The environment is not 32 or 64-bit."
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__ || defined(__BYTE_ORDER) && __BYTE_ORDER == __BIG_ENDIAN || defined(__BIG_ENDIAN__) || defined(__ARMEB__) || defined(__THUMBEB__) || defined(__AARCH64EB__) || defined(_MIBSEB) || defined(__MIBSEB) || defined(__MIBSEB__)
|
||||||
|
#define TARGET_ORDER_IS_BIG
|
||||||
|
#elif defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__ || defined(__BYTE_ORDER) && __BYTE_ORDER == __LITTLE_ENDIAN || defined(__LITTLE_ENDIAN__) || defined(__ARMEL__) || defined(__THUMBEL__) || defined(__AARCH64EL__) || defined(_MIPSEL) || defined(__MIPSEL) || defined(__MIPSEL__) || defined(_M_AMD64) || defined(_M_X64) || defined(_M_IX86)
|
||||||
|
#define TARGET_ORDER_IS_LITTLE
|
||||||
|
#else
|
||||||
|
#error "Unknown architecture endianness"
|
||||||
|
#endif
|
||||||
|
|
||||||
#ifndef _WIN32
|
#ifndef _WIN32
|
||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
#include <locale.h> // tolower
|
#include <locale.h> // tolower
|
||||||
|
|
|
@ -62,11 +62,20 @@ fn (p mut Parser) comp_time() {
|
||||||
p.genln('#endif')
|
p.genln('#endif')
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else if name == 'x64' {
|
||||||
|
p.comptime_if_block('TARGET_IS_64BIT')
|
||||||
|
}
|
||||||
|
else if name == 'x32' {
|
||||||
|
p.comptime_if_block('TARGET_IS_32BIT')
|
||||||
|
}
|
||||||
|
else if name == 'big_endian' {
|
||||||
|
p.comptime_if_block('TARGET_ORDER_IS_BIG')
|
||||||
|
}
|
||||||
|
else if name == 'little_endian' {
|
||||||
|
p.comptime_if_block('TARGET_ORDER_IS_LITTLE')
|
||||||
|
}
|
||||||
else if name == 'debug' {
|
else if name == 'debug' {
|
||||||
p.genln('#ifdef VDEBUG')
|
p.comptime_if_block('VDEBUG')
|
||||||
p.check(.lcbr)
|
|
||||||
p.statements_no_rcbr()
|
|
||||||
p.genln('#endif')
|
|
||||||
}
|
}
|
||||||
else if name == 'tinyc' {
|
else if name == 'tinyc' {
|
||||||
p.comptime_if_block('__TINYC__')
|
p.comptime_if_block('__TINYC__')
|
||||||
|
|
|
@ -0,0 +1,26 @@
|
||||||
|
|
||||||
|
fn test_bitness(){
|
||||||
|
mut x := 0
|
||||||
|
$if x32 {
|
||||||
|
println('system is 32 bit')
|
||||||
|
x = 1
|
||||||
|
}
|
||||||
|
$if x64 {
|
||||||
|
println('system is 64 bit')
|
||||||
|
x = 2
|
||||||
|
}
|
||||||
|
assert x > 0
|
||||||
|
}
|
||||||
|
|
||||||
|
fn test_endianness(){
|
||||||
|
mut x := 0
|
||||||
|
$if little_endian {
|
||||||
|
println('system is little endian')
|
||||||
|
x = 1
|
||||||
|
}
|
||||||
|
$if big_endian {
|
||||||
|
println('system is big endian')
|
||||||
|
x = 2
|
||||||
|
}
|
||||||
|
assert x > 0
|
||||||
|
}
|
|
@ -806,14 +806,14 @@ pub fn chdir(path string) {
|
||||||
pub fn getwd() string {
|
pub fn getwd() string {
|
||||||
$if windows {
|
$if windows {
|
||||||
max := 512 // MAX_PATH * sizeof(wchar_t)
|
max := 512 // MAX_PATH * sizeof(wchar_t)
|
||||||
buf := &u16(malloc(max*2))
|
buf := &u16(calloc(max*2))
|
||||||
if C._wgetcwd(buf, max) == 0 {
|
if C._wgetcwd(buf, max) == 0 {
|
||||||
return ''
|
return ''
|
||||||
}
|
}
|
||||||
return string_from_wide(buf)
|
return string_from_wide(buf)
|
||||||
}
|
}
|
||||||
$else {
|
$else {
|
||||||
buf := malloc(512)
|
buf := calloc(512)
|
||||||
if C.getcwd(buf, 512) == 0 {
|
if C.getcwd(buf, 512) == 0 {
|
||||||
return ''
|
return ''
|
||||||
}
|
}
|
||||||
|
@ -827,7 +827,7 @@ pub fn getwd() string {
|
||||||
// and https://insanecoding.blogspot.com/2007/11/implementing-realpath-in-c.html
|
// and https://insanecoding.blogspot.com/2007/11/implementing-realpath-in-c.html
|
||||||
// NB: this particular rabbit hole is *deep* ...
|
// NB: this particular rabbit hole is *deep* ...
|
||||||
pub fn realpath(fpath string) string {
|
pub fn realpath(fpath string) string {
|
||||||
mut fullpath := malloc( MAX_PATH )
|
mut fullpath := calloc( MAX_PATH )
|
||||||
mut res := 0
|
mut res := 0
|
||||||
$if windows {
|
$if windows {
|
||||||
res = int( C._fullpath( fullpath, fpath.str, MAX_PATH ) )
|
res = int( C._fullpath( fullpath, fpath.str, MAX_PATH ) )
|
||||||
|
|
|
@ -4,8 +4,6 @@
|
||||||
|
|
||||||
module runtime
|
module runtime
|
||||||
|
|
||||||
import os
|
|
||||||
|
|
||||||
//$if linux {
|
//$if linux {
|
||||||
fn C.sysconf(name int) i64
|
fn C.sysconf(name int) i64
|
||||||
//}
|
//}
|
||||||
|
@ -15,18 +13,32 @@ fn C.GetCurrentProcessorNumber() u32
|
||||||
//}
|
//}
|
||||||
|
|
||||||
pub fn nr_cpus() int {
|
pub fn nr_cpus() int {
|
||||||
$if linux {
|
|
||||||
return int(C.sysconf(C._SC_NPROCESSORS_ONLN))
|
|
||||||
}
|
|
||||||
$if mac {
|
|
||||||
return int(C.sysconf(C._SC_NPROCESSORS_ONLN))
|
|
||||||
}
|
|
||||||
$if windows {
|
$if windows {
|
||||||
mut nr := int(C.GetCurrentProcessorNumber())
|
return nr_cpus_win()
|
||||||
if nr == 0 {
|
|
||||||
nr = os.getenv('NUMBER_OF_PROCESSORS').int()
|
|
||||||
}
|
|
||||||
return nr
|
|
||||||
}
|
}
|
||||||
return 1
|
return nr_cpus_nix()
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_32bit() bool {
|
||||||
|
mut x := false
|
||||||
|
$if x32 { x = true }
|
||||||
|
return x
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_64bit() bool {
|
||||||
|
mut x := false
|
||||||
|
$if x64 { x = true }
|
||||||
|
return x
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_little_endian() bool {
|
||||||
|
mut x := false
|
||||||
|
$if little_endian { x = true }
|
||||||
|
return x
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn is_big_endian() bool {
|
||||||
|
mut x := false
|
||||||
|
$if big_endian { x = true }
|
||||||
|
return x
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,16 @@
|
||||||
|
module runtime
|
||||||
|
|
||||||
|
fn nr_cpus_nix() int {
|
||||||
|
$if linux {
|
||||||
|
return int(C.sysconf(C._SC_NPROCESSORS_ONLN))
|
||||||
|
}
|
||||||
|
$if mac {
|
||||||
|
return int(C.sysconf(C._SC_NPROCESSORS_ONLN))
|
||||||
|
}
|
||||||
|
return 1
|
||||||
|
}
|
||||||
|
|
||||||
|
fn nr_cpus_win() int {
|
||||||
|
eprintln('nr_cpus_win should be callable only for windows')
|
||||||
|
return 1
|
||||||
|
}
|
|
@ -4,3 +4,31 @@ fn test_nr_cpus() {
|
||||||
nr_cpus := runtime.nr_cpus()
|
nr_cpus := runtime.nr_cpus()
|
||||||
assert nr_cpus > 0
|
assert nr_cpus > 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn test_is_32bit(){
|
||||||
|
x := runtime.is_32bit().str()
|
||||||
|
assert x == 'true' || x == 'false'
|
||||||
|
}
|
||||||
|
|
||||||
|
fn test_is_64bit(){
|
||||||
|
x := runtime.is_64bit().str()
|
||||||
|
assert x == 'true' || x == 'false'
|
||||||
|
}
|
||||||
|
|
||||||
|
fn test_is_little_endian(){
|
||||||
|
x := runtime.is_little_endian().str()
|
||||||
|
assert x == 'true' || x == 'false'
|
||||||
|
}
|
||||||
|
|
||||||
|
fn test_is_big_endian(){
|
||||||
|
x := runtime.is_big_endian().str()
|
||||||
|
assert x == 'true' || x == 'false'
|
||||||
|
}
|
||||||
|
|
||||||
|
fn test_is_big_endian_different_than_is_little_endian(){
|
||||||
|
assert runtime.is_big_endian() != runtime.is_little_endian()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn test_is_32bit_different_than_is_64bit(){
|
||||||
|
assert runtime.is_32bit() != runtime.is_64bit()
|
||||||
|
}
|
||||||
|
|
|
@ -1 +1,16 @@
|
||||||
module runtime
|
module runtime
|
||||||
|
|
||||||
|
import os
|
||||||
|
|
||||||
|
fn nr_cpus_win() int {
|
||||||
|
mut nr := int(C.GetCurrentProcessorNumber())
|
||||||
|
if nr == 0 {
|
||||||
|
nr = os.getenv('NUMBER_OF_PROCESSORS').int()
|
||||||
|
}
|
||||||
|
return nr
|
||||||
|
}
|
||||||
|
|
||||||
|
fn nr_cpus_nix() int {
|
||||||
|
eprintln('nr_cpus_nix should be callable only for nix platforms')
|
||||||
|
return 1
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in New Issue