mirror of
https://github.com/Ed94/Odin.git
synced 2026-07-29 19:00:06 +00:00
oh boy, basic osx/unix support
This commit is contained in:
+92
@@ -22,6 +22,7 @@ typedef struct BuildContext {
|
||||
String const WIN32_SEPARATOR_STRING = {cast(u8 *)"\\", 1};
|
||||
String const NIX_SEPARATOR_STRING = {cast(u8 *)"/", 1};
|
||||
|
||||
#if defined(WINDOWS)
|
||||
String odin_root_dir(void) {
|
||||
String path = global_module_path;
|
||||
Array(wchar_t) path_buf;
|
||||
@@ -71,6 +72,83 @@ String odin_root_dir(void) {
|
||||
return path;
|
||||
}
|
||||
|
||||
#elif defined(GB_SYSTEM_OSX)
|
||||
|
||||
#include <mach-o/dyld.h>
|
||||
|
||||
String odin_root_dir(void) {
|
||||
String path = global_module_path;
|
||||
Array(char) path_buf;
|
||||
isize len, i;
|
||||
gbTempArenaMemory tmp;
|
||||
wchar_t *text;
|
||||
|
||||
if (global_module_path_set) {
|
||||
return global_module_path;
|
||||
}
|
||||
|
||||
array_init_count(&path_buf, heap_allocator(), 300);
|
||||
|
||||
len = 0;
|
||||
for (;;) {
|
||||
int sz = path_buf.count;
|
||||
int res = _NSGetExecutablePath(&path_buf.e[0], &sz);
|
||||
if(res == 0) {
|
||||
len = sz;
|
||||
break;
|
||||
} else {
|
||||
array_resize(&path_buf, sz + 1);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
tmp = gb_temp_arena_memory_begin(&string_buffer_arena);
|
||||
text = gb_alloc_array(string_buffer_allocator, u8, len + 1);
|
||||
gb_memmove(text, &path_buf.e[0], len);
|
||||
|
||||
path = make_string(text, len);
|
||||
for (i = path.len-1; i >= 0; i--) {
|
||||
u8 c = path.text[i];
|
||||
if (c == '/' || c == '\\') {
|
||||
break;
|
||||
}
|
||||
path.len--;
|
||||
}
|
||||
|
||||
global_module_path = path;
|
||||
global_module_path_set = true;
|
||||
|
||||
gb_temp_arena_memory_end(tmp);
|
||||
|
||||
// array_free(&path_buf);
|
||||
|
||||
return path;
|
||||
}
|
||||
#else
|
||||
#error Implement system
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#if defined(GB_SYSTEM_WINDOWS)
|
||||
String path_to_fullpath(gbAllocator a, String s) {
|
||||
gbTempArenaMemory tmp = gb_temp_arena_memory_begin(&string_buffer_arena);
|
||||
String16 string16 = string_to_string16(string_buffer_allocator, s);
|
||||
@@ -86,6 +164,17 @@ String path_to_fullpath(gbAllocator a, String s) {
|
||||
gb_temp_arena_memory_end(tmp);
|
||||
return result;
|
||||
}
|
||||
#elif defined(GB_SYSTEM_OSX) || defined(GB_SYSTEM_UNIX)
|
||||
String path_to_fullpath(gbAllocator a, String s) {
|
||||
char* p = realpath(s.text, 0);
|
||||
// GB_ASSERT(p && "file does not exist");
|
||||
if(!p) return make_string_c("");
|
||||
|
||||
return make_string(p, strlen(p));
|
||||
}
|
||||
#else
|
||||
#error Implement system
|
||||
#endif
|
||||
|
||||
|
||||
String get_fullpath_relative(gbAllocator a, String base_dir, String path) {
|
||||
@@ -154,6 +243,9 @@ void init_build_context(BuildContext *bc) {
|
||||
#if defined(GB_SYSTEM_WINDOWS)
|
||||
bc->ODIN_OS = str_lit("windows");
|
||||
bc->ODIN_ARCH = str_lit("amd64");
|
||||
#elif defined(GB_SYSTEM_OSX)
|
||||
bc->ODIN_OS = str_lit("osx");
|
||||
bc->ODIN_ARCH = str_lit("amd64");
|
||||
#else
|
||||
#error Implement system
|
||||
#endif
|
||||
|
||||
+1
-1
@@ -69,7 +69,7 @@ void check_init_variables(Checker *c, Entity **lhs, isize lhs_count, AstNodeArra
|
||||
AstNode *rhs = inits.e[i];
|
||||
Operand o = {0};
|
||||
check_multi_expr(c, &o, rhs);
|
||||
if (o.type->kind != Type_Tuple) {
|
||||
if (o.type == NULL || o.type->kind != Type_Tuple) {
|
||||
array_add(&operands, o);
|
||||
} else {
|
||||
TypeTuple *tuple = &o.type->Tuple;
|
||||
|
||||
+5
-1
@@ -225,6 +225,9 @@ i64 check_distance_between_types(Checker *c, Operand *operand, Type *type) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
#ifndef _MAX
|
||||
#define _MAX(x, y) ((x) > (y) ? (x) : (y))
|
||||
#endif
|
||||
|
||||
bool check_is_assignable_to_with_score(Checker *c, Operand *operand, Type *type, i64 *score_) {
|
||||
i64 score = 0;
|
||||
@@ -232,7 +235,8 @@ bool check_is_assignable_to_with_score(Checker *c, Operand *operand, Type *type,
|
||||
bool ok = distance >= 0;
|
||||
if (ok) {
|
||||
// TODO(bill): A decent score function
|
||||
score = max(1000000 - distance*distance, 0);
|
||||
// score = max(1000000 - distance*distance, 0);
|
||||
score = _MAX(1000000 - distance*distance, 0);
|
||||
}
|
||||
if (score_) *score_ = score;
|
||||
return ok;
|
||||
|
||||
@@ -724,6 +724,7 @@ void check_stmt_internal(Checker *c, AstNode *node, u32 flags) {
|
||||
}
|
||||
|
||||
skip_expr:
|
||||
; // again, declaring a variable immediately after a label... weird.
|
||||
AstNode *lhs[2] = {rs->value, rs->index};
|
||||
Type * rhs[2] = {val, idx};
|
||||
|
||||
|
||||
@@ -118,47 +118,6 @@ typedef enum StmtFlag {
|
||||
Stmt_GiveAllowed = 1<<3,
|
||||
} StmtFlag;
|
||||
|
||||
typedef enum BuiltinProcId {
|
||||
BuiltinProc_Invalid,
|
||||
|
||||
BuiltinProc_new,
|
||||
BuiltinProc_new_slice,
|
||||
BuiltinProc_free,
|
||||
|
||||
BuiltinProc_reserve,
|
||||
BuiltinProc_append,
|
||||
|
||||
BuiltinProc_size_of,
|
||||
BuiltinProc_size_of_val,
|
||||
BuiltinProc_align_of,
|
||||
BuiltinProc_align_of_val,
|
||||
BuiltinProc_offset_of,
|
||||
BuiltinProc_offset_of_val,
|
||||
BuiltinProc_type_of_val,
|
||||
|
||||
BuiltinProc_type_info,
|
||||
BuiltinProc_type_info_of_val,
|
||||
|
||||
BuiltinProc_compile_assert,
|
||||
BuiltinProc_assert,
|
||||
BuiltinProc_panic,
|
||||
|
||||
BuiltinProc_copy,
|
||||
// BuiltinProc_append,
|
||||
|
||||
BuiltinProc_swizzle,
|
||||
|
||||
// BuiltinProc_ptr_offset,
|
||||
// BuiltinProc_ptr_sub,
|
||||
BuiltinProc_slice_ptr,
|
||||
|
||||
BuiltinProc_min,
|
||||
BuiltinProc_max,
|
||||
BuiltinProc_abs,
|
||||
BuiltinProc_clamp,
|
||||
|
||||
BuiltinProc_Count,
|
||||
} BuiltinProcId;
|
||||
typedef struct BuiltinProc {
|
||||
String name;
|
||||
isize arg_count;
|
||||
@@ -205,13 +164,6 @@ gb_global BuiltinProc builtin_procs[BuiltinProc_Count] = {
|
||||
{STR_LIT("clamp"), 3, false, Expr_Expr},
|
||||
};
|
||||
|
||||
typedef enum ImplicitValueId {
|
||||
ImplicitValue_Invalid,
|
||||
|
||||
ImplicitValue_context,
|
||||
|
||||
ImplicitValue_Count,
|
||||
} ImplicitValueId;
|
||||
typedef struct ImplicitValueInfo {
|
||||
String name;
|
||||
String backing_name;
|
||||
|
||||
+59
-2
@@ -1,8 +1,65 @@
|
||||
typedef struct Scope Scope;
|
||||
typedef struct Checker Checker;
|
||||
typedef struct Type Type;
|
||||
typedef enum BuiltinProcId BuiltinProcId;
|
||||
typedef enum ImplicitValueId ImplicitValueId;
|
||||
// typedef enum BuiltinProcId BuiltinProcId;
|
||||
// typedef enum ImplicitValueId ImplicitValueId;
|
||||
|
||||
|
||||
|
||||
typedef enum BuiltinProcId {
|
||||
BuiltinProc_Invalid,
|
||||
|
||||
BuiltinProc_new,
|
||||
BuiltinProc_new_slice,
|
||||
BuiltinProc_free,
|
||||
|
||||
BuiltinProc_reserve,
|
||||
BuiltinProc_append,
|
||||
|
||||
BuiltinProc_size_of,
|
||||
BuiltinProc_size_of_val,
|
||||
BuiltinProc_align_of,
|
||||
BuiltinProc_align_of_val,
|
||||
BuiltinProc_offset_of,
|
||||
BuiltinProc_offset_of_val,
|
||||
BuiltinProc_type_of_val,
|
||||
|
||||
BuiltinProc_type_info,
|
||||
BuiltinProc_type_info_of_val,
|
||||
|
||||
BuiltinProc_compile_assert,
|
||||
BuiltinProc_assert,
|
||||
BuiltinProc_panic,
|
||||
|
||||
BuiltinProc_copy,
|
||||
// BuiltinProc_append,
|
||||
|
||||
BuiltinProc_swizzle,
|
||||
|
||||
// BuiltinProc_ptr_offset,
|
||||
// BuiltinProc_ptr_sub,
|
||||
BuiltinProc_slice_ptr,
|
||||
|
||||
BuiltinProc_min,
|
||||
BuiltinProc_max,
|
||||
BuiltinProc_abs,
|
||||
BuiltinProc_clamp,
|
||||
|
||||
BuiltinProc_Count,
|
||||
} BuiltinProcId;
|
||||
|
||||
|
||||
typedef enum ImplicitValueId {
|
||||
ImplicitValue_Invalid,
|
||||
|
||||
ImplicitValue_context,
|
||||
|
||||
ImplicitValue_Count,
|
||||
} ImplicitValueId;
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#define ENTITY_KINDS \
|
||||
ENTITY_KIND(Invalid) \
|
||||
|
||||
@@ -416,6 +416,7 @@ ExactValue exact_binary_operator_value(TokenKind op, ExactValue x, ExactValue y)
|
||||
}
|
||||
|
||||
error:
|
||||
; // MSVC accepts this??? apparently you cannot declare variables immediately after labels...
|
||||
ExactValue error_value = {0};
|
||||
// gb_printf_err("Invalid binary operation: %s\n", token_kind_to_string(op));
|
||||
return error_value;
|
||||
|
||||
+20
-3
@@ -276,6 +276,8 @@ extern "C" {
|
||||
#include <stdarg.h>
|
||||
#include <stddef.h>
|
||||
|
||||
|
||||
|
||||
#if defined(GB_SYSTEM_WINDOWS)
|
||||
#if !defined(GB_NO_WINDOWS_H)
|
||||
#define NOMINMAX 1
|
||||
@@ -296,6 +298,7 @@ extern "C" {
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <pthread.h>
|
||||
#define _IOSC11_SOURCE
|
||||
#include <stdlib.h> // NOTE(bill): malloc on linux
|
||||
#include <sys/mman.h>
|
||||
#if !defined(GB_SYSTEM_OSX)
|
||||
@@ -4819,14 +4822,17 @@ GB_ALLOCATOR_PROC(gb_heap_allocator_proc) {
|
||||
#else
|
||||
// TODO(bill): *nix version that's decent
|
||||
case gbAllocation_Alloc: {
|
||||
ptr = aligned_alloc(alignment, size);
|
||||
// ptr = aligned_alloc(alignment, size);
|
||||
|
||||
posix_memalign(&ptr, alignment, size);
|
||||
|
||||
if (flags & gbAllocatorFlag_ClearToZero) {
|
||||
gb_zero_size(ptr, size);
|
||||
}
|
||||
} break;
|
||||
|
||||
case gbAllocation_Free: {
|
||||
free(gb_allocation_header(old_memory));
|
||||
// free(old_memory);
|
||||
} break;
|
||||
|
||||
case gbAllocation_Resize: {
|
||||
@@ -7754,7 +7760,18 @@ char *gb_path_get_full_name(gbAllocator a, char const *path) {
|
||||
return gb_alloc_str_len(a, buf, len+1);
|
||||
#else
|
||||
// TODO(bill): Make work on *nix, etc.
|
||||
return gb_alloc_str_len(a, path, gb_strlen(path));
|
||||
char* p = realpath(path, 0);
|
||||
GB_ASSERT(p && "file does not exist");
|
||||
|
||||
isize len = gb_strlen(p);
|
||||
|
||||
// bill... gb_alloc_str_len refused to work for this...
|
||||
char* ret = gb_alloc(a, sizeof(char) * len + 1);
|
||||
gb_memmove(ret, p, len);
|
||||
ret[len] = 0;
|
||||
free(p);
|
||||
|
||||
return ret;
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
+56
-7
@@ -16,8 +16,10 @@ extern "C" {
|
||||
#include "ir_print.c"
|
||||
// #include "vm.c"
|
||||
|
||||
#if defined(GB_SYSTEM_WINDOWS)
|
||||
|
||||
// NOTE(bill): `name` is used in debugging and profiling modes
|
||||
i32 win32_exec_command_line_app(char *name, bool is_silent, char *fmt, ...) {
|
||||
i32 system_exec_command_line_app(char *name, bool is_silent, char *fmt, ...) {
|
||||
STARTUPINFOW start_info = {gb_size_of(STARTUPINFOW)};
|
||||
PROCESS_INFORMATION pi = {0};
|
||||
char cmd_line[4096] = {0};
|
||||
@@ -59,6 +61,53 @@ i32 win32_exec_command_line_app(char *name, bool is_silent, char *fmt, ...) {
|
||||
gb_temp_arena_memory_end(tmp);
|
||||
return exit_code;
|
||||
}
|
||||
#elif defined(GB_SYSTEM_OSX) || defined(GB_SYSTEM_UNIX)
|
||||
i32 system_exec_command_line_app(char *name, bool is_silent, char *fmt, ...) {
|
||||
|
||||
char cmd_line[4096] = {0};
|
||||
isize cmd_len;
|
||||
va_list va;
|
||||
String cmd;
|
||||
i32 exit_code = 0;
|
||||
|
||||
va_start(va, fmt);
|
||||
cmd_len = gb_snprintf_va(cmd_line, gb_size_of(cmd_line), fmt, va);
|
||||
va_end(va);
|
||||
|
||||
exit_code = system(cmd.text);
|
||||
|
||||
// pid_t pid = fork();
|
||||
// int status = 0;
|
||||
|
||||
// if(pid == 0) {
|
||||
// // in child, pid == 0.
|
||||
// int ret = execvp(cmd.text, (char* const*) cmd.text);
|
||||
|
||||
// if(ret == -1) {
|
||||
// gb_printf_err("Failed to execute command:\n\t%s\n", cmd_line);
|
||||
|
||||
// // we're in the child, so returning won't do us any good -- just quit.
|
||||
// exit(-1);
|
||||
// }
|
||||
|
||||
// // unreachable
|
||||
// abort();
|
||||
// } else {
|
||||
// // wait for child to finish, then we can continue cleanup
|
||||
|
||||
// int s = 0;
|
||||
// waitpid(pid, &s, 0);
|
||||
|
||||
// status = WEXITSTATUS(s);
|
||||
// }
|
||||
|
||||
// exit_code = status;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
void print_usage_line(i32 indent, char *fmt, ...) {
|
||||
while (indent --> 0) {
|
||||
@@ -190,7 +239,7 @@ int main(int argc, char **argv) {
|
||||
|
||||
// prof_print_all();
|
||||
|
||||
#if 1
|
||||
#if 1
|
||||
timings_start_section(&timings, str_lit("llvm-opt"));
|
||||
|
||||
char const *output_name = ir_gen.output_file.filename;
|
||||
@@ -202,7 +251,7 @@ int main(int argc, char **argv) {
|
||||
|
||||
i32 exit_code = 0;
|
||||
// For more passes arguments: http://llvm.org/docs/Passes.html
|
||||
exit_code = win32_exec_command_line_app("llvm-opt", false,
|
||||
exit_code = system_exec_command_line_app("llvm-opt", false,
|
||||
"\"%.*sbin/opt\" \"%s\" -o \"%.*s\".bc "
|
||||
"-mem2reg "
|
||||
"-memcpyopt "
|
||||
@@ -217,10 +266,10 @@ int main(int argc, char **argv) {
|
||||
return exit_code;
|
||||
}
|
||||
|
||||
#if 1
|
||||
#if 0
|
||||
timings_start_section(&timings, str_lit("llvm-llc"));
|
||||
// For more arguments: http://llvm.org/docs/CommandGuide/llc.html
|
||||
exit_code = win32_exec_command_line_app("llvm-llc", false,
|
||||
exit_code = system_exec_command_line_app("llvm-llc", false,
|
||||
"\"%.*sbin/llc\" \"%.*s.bc\" -filetype=obj -O%d "
|
||||
"%.*s "
|
||||
// "-debug-pass=Arguments "
|
||||
@@ -255,7 +304,7 @@ int main(int argc, char **argv) {
|
||||
link_settings = "/ENTRY:mainCRTStartup";
|
||||
}
|
||||
|
||||
exit_code = win32_exec_command_line_app("msvc-link", true,
|
||||
exit_code = system_exec_command_line_app("msvc-link", true,
|
||||
"link \"%.*s\".obj -OUT:\"%.*s.%s\" %s "
|
||||
"/defaultlib:libcmt "
|
||||
"/nologo /incremental:no /opt:ref /subsystem:CONSOLE "
|
||||
@@ -273,7 +322,7 @@ int main(int argc, char **argv) {
|
||||
// timings_print_all(&timings);
|
||||
|
||||
if (run_output) {
|
||||
win32_exec_command_line_app("odin run", false, "%.*s.exe", cast(int)base_name_len, output_name);
|
||||
system_exec_command_line_app("odin run", false, "%.*s.exe", cast(int)base_name_len, output_name);
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -3785,6 +3785,7 @@ ParseFileError parse_files(Parser *p, char *init_filename) {
|
||||
String import_rel_path = imported_file.rel_path;
|
||||
TokenPos pos = imported_file.pos;
|
||||
AstFile file = {0};
|
||||
|
||||
ParseFileError err = init_ast_file(&file, import_path);
|
||||
|
||||
if (err != ParseFile_None) {
|
||||
|
||||
+52
-9
@@ -165,6 +165,54 @@ bool string_contains_char(String s, u8 c) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#if defined(GB_SYSTEM_WINDOWS)
|
||||
|
||||
int convert_multibyte_to_widechar(char* multibyte_input, int input_length, wchar_t* output, int output_size)
|
||||
{
|
||||
return MultiByteToWideChar(CP_UTF8, MB_ERR_INVALID_CHARS, multibyte_input, input_length, output, output_size);
|
||||
}
|
||||
|
||||
int convert_widechar_to_multibyte(wchar_t* widechar_input, int input_length, char* output, int output_size)
|
||||
{
|
||||
return WideCharToMultiByte(CP_UTF8, WC_ERR_INVALID_CHARS, widechar_input, input_length, output, output_size, NULL, NULL);
|
||||
}
|
||||
}
|
||||
#elif defined(GB_SYSTEM_UNIX) || defined(GB_SYSTEM_OSX)
|
||||
|
||||
#include <iconv.h>
|
||||
|
||||
int convert_multibyte_to_widechar(char* multibyte_input, int input_length, wchar_t* output, int output_size)
|
||||
{
|
||||
iconv_t conv = iconv_open("WCHAR_T", "UTF-8");
|
||||
size_t result = iconv(conv, (char**) &multibyte_input, &input_length, (char**) &output, &output_size);
|
||||
iconv_close(conv);
|
||||
|
||||
return (int) result;
|
||||
}
|
||||
|
||||
int convert_widechar_to_multibyte(wchar_t* widechar_input, int input_length, char* output, int output_size)
|
||||
{
|
||||
iconv_t conv = iconv_open("UTF-8", "WCHAR_T");
|
||||
size_t result = iconv(conv, (char**) &widechar_input, &input_length, (char**) &output, &output_size);
|
||||
iconv_close(conv);
|
||||
|
||||
return (int) result;
|
||||
}
|
||||
#else
|
||||
#error Implement system
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
// TODO(bill): Make this non-windows specific
|
||||
String16 string_to_string16(gbAllocator a, String s) {
|
||||
int len, len1;
|
||||
@@ -174,16 +222,14 @@ String16 string_to_string16(gbAllocator a, String s) {
|
||||
return make_string16(NULL, 0);
|
||||
}
|
||||
|
||||
len = MultiByteToWideChar(CP_UTF8, MB_ERR_INVALID_CHARS,
|
||||
cast(char *)s.text, s.len, NULL, 0);
|
||||
len = convert_multibyte_to_widechar(cast(char *)s.text, s.len, NULL, 0);
|
||||
if (len == 0) {
|
||||
return make_string16(NULL, 0);
|
||||
}
|
||||
|
||||
text = gb_alloc_array(a, wchar_t, len+1);
|
||||
|
||||
len1 = MultiByteToWideChar(CP_UTF8, MB_ERR_INVALID_CHARS,
|
||||
cast(char *)s.text, s.len, text, len);
|
||||
len1 = convert_multibyte_to_widechar(cast(char *)s.text, s.len, text, len);
|
||||
if (len1 == 0) {
|
||||
gb_free(a, text);
|
||||
return make_string16(NULL, 0);
|
||||
@@ -201,16 +247,14 @@ String string16_to_string(gbAllocator a, String16 s) {
|
||||
return make_string(NULL, 0);
|
||||
}
|
||||
|
||||
len = WideCharToMultiByte(CP_UTF8, WC_ERR_INVALID_CHARS,
|
||||
s.text, s.len, NULL, 0, NULL, NULL);
|
||||
len = convert_widechar_to_multibyte(s.text, s.len, NULL, 0);
|
||||
if (len == 0) {
|
||||
return make_string(NULL, 0);
|
||||
}
|
||||
|
||||
text = gb_alloc_array(a, u8, len+1);
|
||||
|
||||
len1 = WideCharToMultiByte(CP_UTF8, WC_ERR_INVALID_CHARS,
|
||||
s.text, s.len, cast(char *)text, len, NULL, NULL);
|
||||
len1 = convert_widechar_to_multibyte(s.text, s.len, cast(char *)text, len);
|
||||
if (len1 == 0) {
|
||||
gb_free(a, text);
|
||||
return make_string(NULL, 0);
|
||||
@@ -236,7 +280,6 @@ String string16_to_string(gbAllocator a, String16 s) {
|
||||
|
||||
|
||||
|
||||
|
||||
bool unquote_char(String s, u8 quote, Rune *rune, bool *multiple_bytes, String *tail_string) {
|
||||
u8 c;
|
||||
|
||||
|
||||
@@ -11,6 +11,7 @@ typedef struct Timings {
|
||||
} Timings;
|
||||
|
||||
|
||||
#if defined(GB_SYSTEM_WINDOWS)
|
||||
u64 win32_time_stamp_time_now(void) {
|
||||
LARGE_INTEGER counter;
|
||||
QueryPerformanceCounter(&counter);
|
||||
@@ -26,10 +27,43 @@ u64 win32_time_stamp__freq(void) {
|
||||
|
||||
return win32_perf_count_freq.QuadPart;
|
||||
}
|
||||
#elif defined(GB_SYSTEM_OSX) || defined(GB_SYSTEM_UNIX)
|
||||
#include <time.h>
|
||||
|
||||
u64 unix_time_stamp_time_now(void) {
|
||||
struct timespec ts;
|
||||
clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &ts);
|
||||
|
||||
return (ts.tv_sec * 1000000000) + ts.tv_nsec;
|
||||
}
|
||||
|
||||
u64 unix_time_stamp__freq(void) {
|
||||
gb_local_persist u64 freq = 0;
|
||||
|
||||
if (freq == 0) {
|
||||
struct timespec ts;
|
||||
clock_getres(CLOCK_PROCESS_CPUTIME_ID, &ts);
|
||||
|
||||
// that would be an absurd resolution (or lack thereof)
|
||||
GB_ASSERT(ts.tv_sec == 0);
|
||||
|
||||
freq = cast(u64) ((1.0 / ts.tv_nsec) * 1000000000.0);
|
||||
|
||||
GB_ASSERT(freq != 0);
|
||||
}
|
||||
|
||||
return freq;
|
||||
}
|
||||
|
||||
#else
|
||||
#error Implement system
|
||||
#endif
|
||||
|
||||
u64 time_stamp_time_now(void) {
|
||||
#if defined(GB_SYSTEM_WINDOWS)
|
||||
return win32_time_stamp_time_now();
|
||||
#elif defined(GB_SYSTEM_OSX) || defined(GB_SYSTEM_UNIX)
|
||||
return unix_time_stamp_time_now();
|
||||
#else
|
||||
#error time_stamp_time_now
|
||||
#endif
|
||||
@@ -38,6 +72,8 @@ u64 time_stamp_time_now(void) {
|
||||
u64 time_stamp__freq(void) {
|
||||
#if defined(GB_SYSTEM_WINDOWS)
|
||||
return win32_time_stamp__freq();
|
||||
#elif defined(GB_SYSTEM_OSX) || defined(GB_SYSTEM_UNIX)
|
||||
return unix_time_stamp__freq();
|
||||
#else
|
||||
#error time_stamp__freq
|
||||
#endif
|
||||
|
||||
+1
-1
@@ -1343,7 +1343,7 @@ void type_path_pop(TypePath *tp) {
|
||||
|
||||
i64 type_size_of(BaseTypeSizes s, gbAllocator allocator, Type *t);
|
||||
i64 type_align_of(BaseTypeSizes s, gbAllocator allocator, Type *t);
|
||||
i64 type_offset_of(BaseTypeSizes s, gbAllocator allocator, Type *t, i64 index);
|
||||
i64 type_offset_of(BaseTypeSizes s, gbAllocator allocator, Type *t, isize index);
|
||||
|
||||
i64 type_size_of_internal (BaseTypeSizes s, gbAllocator allocator, Type *t, TypePath *path);
|
||||
i64 type_align_of_internal(BaseTypeSizes s, gbAllocator allocator, Type *t, TypePath *path);
|
||||
|
||||
Reference in New Issue
Block a user