fp: Migrate to custom build script
This commit is contained in:
parent
4ec2bb7b63
commit
c63bdcacb4
1
.gitignore
vendored
1
.gitignore
vendored
@ -1,2 +1,3 @@
|
|||||||
Build/
|
Build/
|
||||||
Nocheckin/
|
Nocheckin/
|
||||||
|
feely_pona_build.exe
|
||||||
|
2
External/tely
vendored
2
External/tely
vendored
@ -1 +1 @@
|
|||||||
Subproject commit 798d1a7d5d98801161992259e24e4aa0c926c14f
|
Subproject commit b21c34597fb1ec7db2f4d240a4bf23bd0a4d96fa
|
102
build.bat
102
build.bat
@ -5,105 +5,15 @@ set script_dir_backslash=%~dp0
|
|||||||
set script_dir=%script_dir_backslash:~0,-1%
|
set script_dir=%script_dir_backslash:~0,-1%
|
||||||
set build_dir=%script_dir%\Build
|
set build_dir=%script_dir%\Build
|
||||||
set code_dir=%script_dir%
|
set code_dir=%script_dir%
|
||||||
set tely_dir=%code_dir%\External\tely
|
|
||||||
|
|
||||||
REM ================================================================================================
|
REM Bootstrap the build program
|
||||||
|
|
||||||
mkdir %build_dir% 2>nul
|
|
||||||
pushd %build_dir%
|
pushd %build_dir%
|
||||||
mkdir %build_dir%\Data 2>nul
|
cl /nologo /Z7 /W4 %code_dir%\feely_pona_build.cpp || exit /B 1
|
||||||
|
copy feely_pona_build.exe %code_dir% 1>nul
|
||||||
|
popd
|
||||||
|
|
||||||
REM ================================================================================================
|
REM Run the build program
|
||||||
|
%code_dir%\feely_pona_build.exe || exit /B 1
|
||||||
set robocopy_cmd=robocopy /MIR /NJH /NJS /NDL /NP %code_dir%\Data %build_dir%\Data
|
|
||||||
call powershell -Command "$duration = Measure-Command {%robocopy_cmd% | Out-Default}; Write-Host 'robocopy:' $duration.TotalSeconds 'seconds'"
|
|
||||||
|
|
||||||
REM ================================================================================================
|
|
||||||
|
|
||||||
REM TODO: Raylib seems to have problems shutting down fsanitize=address?
|
|
||||||
set common_compile_flags=/W4 /Z7 /MT /EHsc /nologo
|
|
||||||
set common_link_flags=/link /incremental:no
|
|
||||||
|
|
||||||
REM raylib =========================================================================================
|
|
||||||
|
|
||||||
set raylib_dir=%tely_dir%\external\raylib
|
|
||||||
if not exist %build_dir%\rcore.obj (
|
|
||||||
cl %common_compile_flags% ^
|
|
||||||
/w ^
|
|
||||||
/c ^
|
|
||||||
/D _DEFAULT_SOURCE ^
|
|
||||||
/D PLATFORM_DESKTOP ^
|
|
||||||
/I %raylib_dir% ^
|
|
||||||
/I %raylib_dir%\external\glfw\include ^
|
|
||||||
/I %raylib_dir%\glfw\deps\mingw ^
|
|
||||||
%raylib_dir%\rcore.c ^
|
|
||||||
%raylib_dir%\utils.c ^
|
|
||||||
%raylib_dir%\raudio.c ^
|
|
||||||
%raylib_dir%\rmodels.c ^
|
|
||||||
%raylib_dir%\rtext.c ^
|
|
||||||
%raylib_dir%\rtextures.c ^
|
|
||||||
%raylib_dir%\rshapes.c ^
|
|
||||||
%raylib_dir%\rglfw.c
|
|
||||||
)
|
|
||||||
|
|
||||||
REM raylib flags =========================================================================================
|
|
||||||
|
|
||||||
set raylib_compile_flags=%common_compile_flags% ^
|
|
||||||
/Tp %tely_dir%\tely_platform_raylib_unity.h ^
|
|
||||||
/I "%raylib_dir%"
|
|
||||||
|
|
||||||
set raylib_link_flags=%common_link_flags% ^
|
|
||||||
%build_dir%\rcore.obj ^
|
|
||||||
%build_dir%\utils.obj ^
|
|
||||||
%build_dir%\raudio.obj ^
|
|
||||||
%build_dir%\rmodels.obj ^
|
|
||||||
%build_dir%\rtext.obj ^
|
|
||||||
%build_dir%\rtextures.obj ^
|
|
||||||
%build_dir%\rshapes.obj ^
|
|
||||||
%build_dir%\rglfw.obj ^
|
|
||||||
gdi32.lib opengl32.lib winmm.lib user32.lib shell32.lib
|
|
||||||
|
|
||||||
REM DLL flags ======================================================================================
|
|
||||||
|
|
||||||
set dll_compile_flags=%common_compile_flags% /LD /Tp %code_dir%\feely_pona_unity.h
|
|
||||||
set dll_link_flags=%common_link_flags%
|
|
||||||
|
|
||||||
REM MSVC commands ==================================================================================
|
|
||||||
|
|
||||||
set msvc_exe_name=feely_pona_msvc
|
|
||||||
set msvc_cmd=cl %raylib_compile_flags% /Fo%msvc_exe_name% /Fe%msvc_exe_name% %raylib_link_flags%
|
|
||||||
set msvc_dll_cmd=cl %dll_compile_flags% /Fotely_dll_msvc /Fetely_dll_msvc %dll_link_flags%
|
|
||||||
|
|
||||||
REM CLANG commands =================================================================================
|
|
||||||
|
|
||||||
set clang_exe_name_sdl=feely_pona_clang
|
|
||||||
set clang_cmd_sdl=clang-cl %compile_flags% /Fo%clang_exe_name_sdl% /Fe%clang_exe_name_sdl% %link_flags%
|
|
||||||
set clang_dll_cmd=clang-cl %dll_compile_flags% /Fotely_dll_clang /Fetely_dll_clang %dll_link_flags%
|
|
||||||
|
|
||||||
REM MSVC build =====================================================================================
|
|
||||||
|
|
||||||
set msvc_build_platform=$platform_time = Measure-Command {%msvc_cmd% ^| Out-Default};
|
|
||||||
set msvc_build_dll=$dll_time = Measure-Command {%msvc_dll_cmd% ^| Out-Default};
|
|
||||||
set msvc_print_platform_and_dll_time=Write-Host 'msvc (platform+dll):'($platform_time.TotalSeconds + $dll_time.TotalSeconds)'s ('$platform_time.TotalSeconds + $dll_time.TotalSeconds')'
|
|
||||||
|
|
||||||
powershell -Command "$file = [System.IO.File]::Open('%build_dir%\%msvc_exe_name%.exe', 'Open', 'Write'); $file.Close(); $file.Dispose()" 2>nul && set msvc_exe_is_locked=0 || set msvc_exe_is_locked=1
|
|
||||||
powershell -Command "$duration = Measure-Command {%msvc_dll_cmd% | Out-Default}; Write-Host 'msvc (dll):' $duration.TotalSeconds 'seconds'"
|
|
||||||
|
|
||||||
echo foo> %msvc_exe_name%.lock
|
|
||||||
if %msvc_exe_is_locked% == 0 (
|
|
||||||
powershell -Command "$time_a = Measure-Command {%msvc_cmd% | Out-Default }; Write-Host 'msvc (raylib):' $time_a.TotalSeconds 'seconds'"
|
|
||||||
)
|
|
||||||
del %msvc_exe_name%.lock
|
|
||||||
|
|
||||||
REM MSVC no-dll ====================================================================================
|
|
||||||
|
|
||||||
set msvc_no_dll_cmd=cl %common_compile_flags% /Tp %code_dir%\feely_pona_unity_nodll.h /Fofeely_pona_msvc_nodll /Fefeely_pona_msvc_nodll %raylib_link_flags%
|
|
||||||
set msvc_sprite_packer_cmd=cl %common_compile_flags% %code_dir%\feely_pona_sprite_packer.cpp /Fofeely_pona_sprite_packer /Fefeely_pona_sprite_packer %common_link_flags%
|
|
||||||
|
|
||||||
powershell -Command "$duration = Measure-Command {%msvc_sprite_packer_cmd% | Out-Default}; Write-Host 'msvc (sprite packer):' $duration.TotalSeconds 'seconds'"
|
|
||||||
powershell -Command "$duration = Measure-Command {%msvc_no_dll_cmd% | Out-Default}; Write-Host 'msvc (no-dll):' $duration.TotalSeconds 'seconds'"
|
|
||||||
|
|
||||||
cl /nologo /Z7 %code_dir%\feely_pona_build.cpp
|
|
||||||
|
|
||||||
popd
|
popd
|
||||||
exit /B 1
|
exit /B 1
|
||||||
|
@ -5,233 +5,114 @@
|
|||||||
#define DQN_IMPLEMENTATION
|
#define DQN_IMPLEMENTATION
|
||||||
#include "External/tely/External/dqn/dqn.h"
|
#include "External/tely/External/dqn/dqn.h"
|
||||||
|
|
||||||
struct Dqn_OSExecuteAsyncHandle
|
#define DQN_CPP_BUILD_IMPLEMENTATION
|
||||||
{
|
#include "External/tely/External/dqn/dqn_cppbuild.h"
|
||||||
void *process;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct Dqn_OSExecuteResult
|
#if 0
|
||||||
{
|
void RebuildProgramIfRequired(int argc, char const **argv)
|
||||||
uint32_t os_error_code;
|
|
||||||
uint32_t exit_code;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct Dqn_CPPBuildCompileFile
|
|
||||||
{
|
|
||||||
Dqn_Slice<Dqn_String8> flags;
|
|
||||||
Dqn_String8 path;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct Dqn_CPPBuildContext
|
|
||||||
{
|
|
||||||
Dqn_Slice<Dqn_CPPBuildCompileFile> compile_files;
|
|
||||||
Dqn_Slice<Dqn_String8> compile_flags;
|
|
||||||
Dqn_Slice<Dqn_String8> include_dirs;
|
|
||||||
Dqn_Slice<Dqn_String8> link_flags;
|
|
||||||
Dqn_String8 build_dir;
|
|
||||||
};
|
|
||||||
|
|
||||||
enum Dqn_CPPBuildStatus
|
|
||||||
{
|
|
||||||
Dqn_CPPBuildStatus_Ok,
|
|
||||||
Dqn_CPPBuildStatus_BuildDirectoryFailedToBeMade,
|
|
||||||
};
|
|
||||||
|
|
||||||
struct Dqn_CPPBuildAsyncResult
|
|
||||||
{
|
|
||||||
Dqn_CPPBuildStatus status;
|
|
||||||
Dqn_OSExecuteAsyncHandle async_handle;
|
|
||||||
};
|
|
||||||
|
|
||||||
Dqn_OSExecuteResult Dqn_OS_ExecuteWait(Dqn_OSExecuteAsyncHandle handle)
|
|
||||||
{
|
|
||||||
Dqn_OSExecuteResult result = {};
|
|
||||||
if (!handle.process)
|
|
||||||
return result;
|
|
||||||
|
|
||||||
DWORD exec_result = WaitForSingleObject(handle.process, INFINITE);
|
|
||||||
if (exec_result == WAIT_FAILED) {
|
|
||||||
result.os_error_code = GetLastError();
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
DWORD exit_status;
|
|
||||||
if (!GetExitCodeProcess(handle.process, &exit_status)) {
|
|
||||||
result.os_error_code = GetLastError();
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
result.exit_code = exit_status;
|
|
||||||
CloseHandle(handle.process);
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
Dqn_OSExecuteAsyncHandle Dqn_OS_ExecuteAsync(Dqn_String8 cmd, Dqn_String8 working_dir)
|
|
||||||
{
|
|
||||||
Dqn_OSExecuteAsyncHandle result = {};
|
|
||||||
#if defined(DQN_OS_WIN32)
|
|
||||||
Dqn_ThreadScratch scratch = Dqn_Thread_GetScratch(nullptr);
|
|
||||||
Dqn_String16 cmd16 = Dqn_Win_String8ToString16(scratch.arena, cmd);
|
|
||||||
Dqn_String16 working_dir16 = Dqn_Win_String8ToString16(scratch.arena, working_dir);
|
|
||||||
|
|
||||||
PROCESS_INFORMATION proc_info = {};
|
|
||||||
STARTUPINFOW startup_info = {};
|
|
||||||
startup_info.cb = sizeof(STARTUPINFOW);
|
|
||||||
startup_info.hStdError = GetStdHandle(STD_ERROR_HANDLE);
|
|
||||||
startup_info.hStdOutput = GetStdHandle(STD_OUTPUT_HANDLE);
|
|
||||||
startup_info.hStdInput = GetStdHandle(STD_INPUT_HANDLE);
|
|
||||||
startup_info.dwFlags |= STARTF_USESTDHANDLES;
|
|
||||||
BOOL create_result = CreateProcessW(nullptr, cmd16.data, nullptr, nullptr, true, 0, nullptr, working_dir16.data, &startup_info, &proc_info);
|
|
||||||
if (!create_result)
|
|
||||||
return result;
|
|
||||||
|
|
||||||
CloseHandle(proc_info.hThread);
|
|
||||||
result.process = proc_info.hProcess;
|
|
||||||
#else
|
|
||||||
pid_t child_pid = fork();
|
|
||||||
if (child_pid < 0) {
|
|
||||||
result.os_error_code = errno;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (child_pid == 0) {
|
|
||||||
if (working_dir.size) {
|
|
||||||
if (chdir(working_dir.data) == -1) {
|
|
||||||
result.os_error_code = errno;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (execvp(cmd.items[0], (char * const*) cmd_null.items) < 0) {
|
|
||||||
result.os_error_code = errno;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
DQN_INVALID_CODE_PATH;
|
|
||||||
}
|
|
||||||
|
|
||||||
result.process = DQN_CAST(void *)child_pid;
|
|
||||||
#endif
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
Dqn_OSExecuteResult Dqn_OS_Execute(Dqn_String8 cmd, Dqn_String8 working_dir)
|
|
||||||
{
|
|
||||||
Dqn_OSExecuteAsyncHandle async_handle = Dqn_OS_ExecuteAsync(cmd, working_dir);
|
|
||||||
Dqn_OSExecuteResult result = Dqn_OS_ExecuteWait(async_handle);
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
Dqn_String8 Dqn_CPPBuildContext_ToCommandLine(Dqn_CPPBuildContext build_context, Dqn_Allocator allocator)
|
|
||||||
{
|
|
||||||
// NOTE: Check if object files are newer than the source files =================================
|
|
||||||
Dqn_ThreadScratch scratch = Dqn_Thread_GetScratch(allocator.user_context);
|
|
||||||
Dqn_Slice<Dqn_CPPBuildCompileFile> dirtied_compile_files = Dqn_Slice_Alloc<Dqn_CPPBuildCompileFile>(scratch.arena, build_context.compile_files.size, Dqn_ZeroMem_Yes);
|
|
||||||
dirtied_compile_files.size = 0;
|
|
||||||
DQN_FOR_UINDEX (index, build_context.compile_files.size) {
|
|
||||||
Dqn_CPPBuildCompileFile file = build_context.compile_files.data[index];
|
|
||||||
Dqn_String8 file_stem = Dqn_String8_FileNameNoExtension(file.path);
|
|
||||||
|
|
||||||
Dqn_String8 obj_file = {};
|
|
||||||
if (build_context.build_dir.size)
|
|
||||||
obj_file = Dqn_FsPath_ConvertF(scratch.arena, "%.*s/%.*s.obj", DQN_STRING_FMT(build_context.build_dir), DQN_STRING_FMT(file_stem));
|
|
||||||
else
|
|
||||||
obj_file = Dqn_FsPath_ConvertF(scratch.arena, "%.*s.obj", DQN_STRING_FMT(file_stem));
|
|
||||||
|
|
||||||
Dqn_FsInfo file_info = Dqn_Fs_GetInfo(file.path);
|
|
||||||
Dqn_FsInfo obj_file_info = Dqn_Fs_GetInfo(obj_file);
|
|
||||||
if (obj_file_info.last_write_time_in_s >= file_info.last_write_time_in_s)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
dirtied_compile_files.data[dirtied_compile_files.size++] = file;
|
|
||||||
}
|
|
||||||
|
|
||||||
Dqn_String8 result = {};
|
|
||||||
if (dirtied_compile_files.size <= 0)
|
|
||||||
return result;
|
|
||||||
|
|
||||||
// NOTE: Build the command line invocation =====================================================
|
|
||||||
Dqn_String8Builder builder = {};
|
|
||||||
builder.allocator = allocator;
|
|
||||||
DQN_FOR_UINDEX (index, build_context.compile_flags.size) {
|
|
||||||
Dqn_String8 flag = build_context.compile_flags.data[index];
|
|
||||||
if (index)
|
|
||||||
Dqn_String8Builder_AppendF(&builder, " ");
|
|
||||||
Dqn_String8Builder_AppendRef(&builder, flag);
|
|
||||||
}
|
|
||||||
|
|
||||||
DQN_FOR_UINDEX (index, build_context.include_dirs.size) {
|
|
||||||
Dqn_String8 include_dir = build_context.include_dirs.data[index];
|
|
||||||
if (builder.count)
|
|
||||||
Dqn_String8Builder_AppendF(&builder, " ");
|
|
||||||
Dqn_String8Builder_AppendF(&builder, "/I %.*s", DQN_STRING_FMT(include_dir));
|
|
||||||
}
|
|
||||||
|
|
||||||
DQN_FOR_UINDEX (index, dirtied_compile_files.size) {
|
|
||||||
Dqn_CPPBuildCompileFile file = dirtied_compile_files.data[index];
|
|
||||||
Dqn_ThreadScratch scratch = Dqn_Thread_GetScratch(allocator.user_context);
|
|
||||||
Dqn_String8 obj_file = {};
|
|
||||||
if (builder.count)
|
|
||||||
Dqn_String8Builder_AppendF(&builder, " ");
|
|
||||||
DQN_FOR_UINDEX (flag_index, file.flags.size) {
|
|
||||||
Dqn_String8 flag = file.flags.data[flag_index];
|
|
||||||
Dqn_String8Builder_AppendF(&builder, "%s%.*s", flag_index ? " " : "", DQN_STRING_FMT(flag));
|
|
||||||
}
|
|
||||||
if (file.flags.size)
|
|
||||||
Dqn_String8Builder_AppendF(&builder, " ");
|
|
||||||
Dqn_String8Builder_AppendRef(&builder, file.path);
|
|
||||||
}
|
|
||||||
|
|
||||||
DQN_FOR_UINDEX (index, build_context.link_flags.size) {
|
|
||||||
Dqn_String8 file = build_context.link_flags.data[index];
|
|
||||||
if (builder.count)
|
|
||||||
Dqn_String8Builder_AppendF(&builder, " ");
|
|
||||||
Dqn_String8Builder_AppendRef(&builder, file);
|
|
||||||
}
|
|
||||||
|
|
||||||
result = Dqn_String8Builder_Build(&builder, allocator);
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
Dqn_CPPBuildAsyncResult Dqn_CPPBuild_Async(Dqn_CPPBuildContext build_context)
|
|
||||||
{
|
{
|
||||||
Dqn_ThreadScratch scratch = Dqn_Thread_GetScratch(nullptr);
|
Dqn_ThreadScratch scratch = Dqn_Thread_GetScratch(nullptr);
|
||||||
Dqn_String8 cmd = Dqn_CPPBuildContext_ToCommandLine(build_context, scratch.allocator);
|
Dqn_String8 const exe_dir = Dqn_OS_EXEDir(scratch.arena);
|
||||||
Dqn_CPPBuildAsyncResult result = {};
|
Dqn_String8 build_program_path = Dqn_OS_EXEPath(scratch.arena);
|
||||||
if (!cmd.size)
|
Dqn_FsInfo build_program_info = Dqn_Fs_GetInfo(build_program_path);
|
||||||
return result;
|
Dqn_FsInfo source_path = Dqn_Fs_GetInfo(Dqn_String8_InitCString8(__FILE__));
|
||||||
|
|
||||||
if (!Dqn_Fs_MakeDir(build_context.build_dir)) {
|
if (!build_program_info.exists) {
|
||||||
result.status = Dqn_CPPBuildStatus_BuildDirectoryFailedToBeMade;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
result.async_handle = Dqn_OS_ExecuteAsync(cmd, build_context.build_dir);
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
void Dqn_CPPBuild_ExecuteOrAbort(Dqn_CPPBuildContext build_context)
|
|
||||||
{
|
|
||||||
Dqn_CPPBuildAsyncResult build_result = Dqn_CPPBuild_Async(build_context);
|
|
||||||
if (build_result.status == Dqn_CPPBuildStatus_BuildDirectoryFailedToBeMade) {
|
|
||||||
Dqn_Log_ErrorF("Failed to make build dir '%.*s'", DQN_STRING_FMT(build_context.build_dir));
|
|
||||||
exit(-1);
|
|
||||||
}
|
|
||||||
|
|
||||||
Dqn_OSExecuteResult exec_result = Dqn_OS_ExecuteWait(build_result.async_handle);
|
|
||||||
if (exec_result.os_error_code) {
|
|
||||||
Dqn_ThreadScratch scratch = Dqn_Thread_GetScratch(nullptr);
|
|
||||||
Dqn_WinError error = Dqn_Win_LastError(scratch.arena);
|
Dqn_WinError error = Dqn_Win_LastError(scratch.arena);
|
||||||
Dqn_Log_ErrorF("Build command could not be executed, error returned was (%d): %.*s", error.code, DQN_STRING_FMT(error.msg));
|
Dqn_Log_WarningF("Failed to get the last write time of the build program '%.*s', skipping rebuild (%d): %.*s",
|
||||||
exit(-1);
|
DQN_STRING_FMT(build_program_path), error.code, DQN_STRING_FMT(error.msg));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!source_path.exists) {
|
||||||
|
Dqn_WinError error = Dqn_Win_LastError(scratch.arena);
|
||||||
|
Dqn_Log_WarningF(
|
||||||
|
"Failed to get the last write time of the build program's source code '%s', skipping rebuild (%d): %.*s",
|
||||||
|
__FILE__, error.code, DQN_STRING_FMT(error.msg));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// NOTE: The build program is newer than the source path, no rebuild required
|
||||||
|
if (source_path.last_write_time_in_s < build_program_info.last_write_time_in_s) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Dqn_Log_InfoF("Build program source code has changed, rebuilding the program (timestamps changed source was %I64u, build program was %I64u)",
|
||||||
|
source_path.last_write_time_in_s,
|
||||||
|
build_program_info.last_write_time_in_s);
|
||||||
|
|
||||||
|
Dqn_String8 temp_build_program_path = Dqn_FsPath_ConvertF(scratch.arena, "%.*s.old", DQN_STRING_FMT(build_program_path));
|
||||||
|
if (!Dqn_Fs_Move(build_program_path, temp_build_program_path, true)) {
|
||||||
|
Dqn_WinError error = Dqn_Win_LastError(scratch.arena);
|
||||||
|
Dqn_Log_WarningF("Failed to backup the build program for rebuilding, skipping rebuild (%d): %.*s", error.code, DQN_STRING_FMT(error.msg));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// NOTE: Rebuild the build program because a change was detected ===============
|
||||||
|
Dqn_String8 rebuild_cmd = Dqn_String8_InitF(scratch.allocator, "cl /Z7 /W4 /nologo %s /incremental:no /link", __FILE__);
|
||||||
|
Dqn_OSExecResult rebuild_result = Dqn_OS_Exec(rebuild_cmd, exe_dir /*working_dir*/);
|
||||||
|
if (rebuild_result.os_error_code) {
|
||||||
|
Dqn_WinError error = Dqn_Win_LastError(scratch.arena);
|
||||||
|
Dqn_Log_ErrorF("Detected change in the build program's source code '%s' but the OS failed to rebuild the program, skipping rebuild (%d): %.*s", __FILE__, error.code, DQN_STRING_FMT(error.msg));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (rebuild_result.exit_code) {
|
||||||
|
Dqn_Fs_Move(temp_build_program_path, build_program_path, true);
|
||||||
|
exit(rebuild_result.exit_code);
|
||||||
|
}
|
||||||
|
|
||||||
|
Dqn_String8Builder builder = {};
|
||||||
|
builder.allocator = scratch.allocator;
|
||||||
|
DQN_FOR_UINDEX (arg_index, argc)
|
||||||
|
Dqn_String8Builder_AppendF(&builder, "%s%s", arg_index ? " " : "", argv[arg_index]);
|
||||||
|
|
||||||
|
Dqn_String8 rebootstrap_cmd = Dqn_String8Builder_Build(&builder, scratch.allocator);
|
||||||
|
Dqn_OSExecResult exec_result = Dqn_OS_Exec(rebootstrap_cmd, exe_dir /*working_dir*/);
|
||||||
|
if (exec_result.os_error_code) {
|
||||||
|
Dqn_WinError error = Dqn_Win_LastError(scratch.arena);
|
||||||
|
Dqn_Log_ErrorF("Detected change in the build program's source code '%s' but the OS failed to rebuild the program, skipping rebuild (%d): %.*s", __FILE__, error.code, DQN_STRING_FMT(error.msg));
|
||||||
|
Dqn_Fs_Move(temp_build_program_path, build_program_path, true);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (exec_result.exit_code)
|
|
||||||
exit(exec_result.exit_code);
|
exit(exec_result.exit_code);
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
int main()
|
#define PRINT_HELP Dqn_Print_StdLnF(Dqn_PrintStd_Out, "USAGE: feely_pona_build [--help|--dry-run]")
|
||||||
|
int main(int argc, char const **argv)
|
||||||
{
|
{
|
||||||
Dqn_Library_Init();
|
Dqn_Library_Init(Dqn_LibraryOnInit_Nil);
|
||||||
|
if (argc > 2) {
|
||||||
|
PRINT_HELP;
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool dry_run = false;
|
||||||
|
if (argc == 2) {
|
||||||
|
Dqn_String8 arg = Dqn_String8_InitCString8(argv[1]);
|
||||||
|
if (arg == DQN_STRING8("--help")) {
|
||||||
|
PRINT_HELP;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (arg == DQN_STRING8("--dry-run")) {
|
||||||
|
dry_run = true;
|
||||||
|
} else {
|
||||||
|
PRINT_HELP;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
RebuildProgramIfRequired(argc, argv);
|
||||||
|
#else
|
||||||
|
Dqn_Print_StdLnF(Dqn_PrintStd_Out, "-- Dqn_CPPBuild v0");
|
||||||
|
#endif
|
||||||
|
|
||||||
|
uint64_t build_timings[2] = {};
|
||||||
|
build_timings[0] = Dqn_OS_PerfCounterNow();
|
||||||
Dqn_ThreadScratch scratch = Dqn_Thread_GetScratch(nullptr);
|
Dqn_ThreadScratch scratch = Dqn_Thread_GetScratch(nullptr);
|
||||||
Dqn_String8 const exe_dir = Dqn_OS_EXEDir(scratch.arena);
|
Dqn_String8 const exe_dir = Dqn_OS_EXEDir(scratch.arena);
|
||||||
Dqn_String8 const build_dir = Dqn_FsPath_ConvertF(scratch.arena, "%.*s/Build", DQN_STRING_FMT(exe_dir));
|
Dqn_String8 const build_dir = Dqn_FsPath_ConvertF(scratch.arena, "%.*s/Build", DQN_STRING_FMT(exe_dir));
|
||||||
@ -257,7 +138,11 @@ int main()
|
|||||||
robocopy_timings[0] = Dqn_OS_PerfCounterNow();
|
robocopy_timings[0] = Dqn_OS_PerfCounterNow();
|
||||||
DQN_DEFER { robocopy_timings[1] = Dqn_OS_PerfCounterNow(); };
|
DQN_DEFER { robocopy_timings[1] = Dqn_OS_PerfCounterNow(); };
|
||||||
Dqn_String8 robocopy_cmd = Dqn_String8_InitF(scratch.allocator, "robocopy /MIR /NJH /NJS /NDL /NP %.*s\\Data %.*s\\Data", DQN_STRING_FMT(exe_dir), DQN_STRING_FMT(build_dir));
|
Dqn_String8 robocopy_cmd = Dqn_String8_InitF(scratch.allocator, "robocopy /MIR /NJH /NJS /NDL /NP %.*s\\Data %.*s\\Data", DQN_STRING_FMT(exe_dir), DQN_STRING_FMT(build_dir));
|
||||||
Dqn_OS_Execute(robocopy_cmd, /*working_dir*/ {});
|
if (dry_run) {
|
||||||
|
Dqn_Print_StdLnF(Dqn_PrintStd_Out, "%.*s\n", DQN_STRING_FMT(robocopy_cmd));
|
||||||
|
} else {
|
||||||
|
Dqn_OS_Exec(robocopy_cmd, /*working_dir*/ {});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// NOTE: Raylib ================================================================================
|
// NOTE: Raylib ================================================================================
|
||||||
@ -302,7 +187,12 @@ int main()
|
|||||||
raylib_build_context.link_flags = common_link_flags;
|
raylib_build_context.link_flags = common_link_flags;
|
||||||
raylib_build_context.build_dir = build_dir;
|
raylib_build_context.build_dir = build_dir;
|
||||||
|
|
||||||
Dqn_CPPBuild_ExecuteOrAbort(raylib_build_context);
|
if (dry_run) {
|
||||||
|
Dqn_String8 cmd = Dqn_CPPBuild_ToCommandLine(raylib_build_context, Dqn_CPPBuildMode_AlwaysRebuild, scratch.allocator);
|
||||||
|
Dqn_Print_StdLnF(Dqn_PrintStd_Out, "%.*s\n", DQN_STRING_FMT(cmd));
|
||||||
|
} else {
|
||||||
|
Dqn_CPPBuild_ExecOrAbort(raylib_build_context, Dqn_CPPBuildMode_CacheBuild);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// NOTE: Feely Pona Sprite Packer ==============================================================
|
// NOTE: Feely Pona Sprite Packer ==============================================================
|
||||||
@ -321,7 +211,7 @@ int main()
|
|||||||
build_context.link_flags = common_link_flags;
|
build_context.link_flags = common_link_flags;
|
||||||
build_context.build_dir = build_dir;
|
build_context.build_dir = build_dir;
|
||||||
|
|
||||||
Dqn_CPPBuild_ExecuteOrAbort(build_context);
|
Dqn_CPPBuild_ExecOrAbort(build_context, Dqn_CPPBuildMode_CacheBuild);
|
||||||
}
|
}
|
||||||
|
|
||||||
// NOTE: Feely Pona No DLL =====================================================================
|
// NOTE: Feely Pona No DLL =====================================================================
|
||||||
@ -335,7 +225,7 @@ int main()
|
|||||||
feely_pona_no_dll_build_context.compile_files = Dqn_Slice_InitCArrayCopy(scratch.arena, {
|
feely_pona_no_dll_build_context.compile_files = Dqn_Slice_InitCArrayCopy(scratch.arena, {
|
||||||
Dqn_CPPBuildCompileFile{
|
Dqn_CPPBuildCompileFile{
|
||||||
{Dqn_Slice_InitCArrayCopy(scratch.arena, {DQN_STRING8("/Tp")})},
|
{Dqn_Slice_InitCArrayCopy(scratch.arena, {DQN_STRING8("/Tp")})},
|
||||||
Dqn_FsPath_ConvertF(scratch.arena, "%.*s/feely_pona_nodll.h", DQN_STRING_FMT(code_dir))
|
Dqn_FsPath_ConvertF(scratch.arena, "%.*s/feely_pona_unity_nodll.h", DQN_STRING_FMT(code_dir))
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -363,7 +253,12 @@ int main()
|
|||||||
feely_pona_no_dll_build_context.link_flags = Dqn_List_ToSliceCopy(&link_flags, scratch.arena);
|
feely_pona_no_dll_build_context.link_flags = Dqn_List_ToSliceCopy(&link_flags, scratch.arena);
|
||||||
feely_pona_no_dll_build_context.build_dir = build_dir;
|
feely_pona_no_dll_build_context.build_dir = build_dir;
|
||||||
|
|
||||||
Dqn_CPPBuild_ExecuteOrAbort(feely_pona_no_dll_build_context);
|
if (dry_run) {
|
||||||
|
Dqn_String8 cmd = Dqn_CPPBuild_ToCommandLine(feely_pona_no_dll_build_context, Dqn_CPPBuildMode_AlwaysRebuild, scratch.allocator);
|
||||||
|
Dqn_Print_StdLnF(Dqn_PrintStd_Out, "%.*s\n", DQN_STRING_FMT(cmd));
|
||||||
|
} else {
|
||||||
|
Dqn_CPPBuild_ExecOrAbort(feely_pona_no_dll_build_context, Dqn_CPPBuildMode_AlwaysRebuild);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// NOTE: Feely Pona DLL ========================================================================
|
// NOTE: Feely Pona DLL ========================================================================
|
||||||
@ -390,7 +285,12 @@ int main()
|
|||||||
build_context.link_flags = feely_pona_no_dll_build_context.link_flags;
|
build_context.link_flags = feely_pona_no_dll_build_context.link_flags;
|
||||||
build_context.build_dir = build_dir;
|
build_context.build_dir = build_dir;
|
||||||
|
|
||||||
Dqn_CPPBuild_ExecuteOrAbort(build_context);
|
if (dry_run) {
|
||||||
|
Dqn_String8 cmd = Dqn_CPPBuild_ToCommandLine(build_context, Dqn_CPPBuildMode_AlwaysRebuild, scratch.allocator);
|
||||||
|
Dqn_Print_StdLnF(Dqn_PrintStd_Out, "%.*s\n", DQN_STRING_FMT(cmd));
|
||||||
|
} else {
|
||||||
|
Dqn_CPPBuild_ExecOrAbort(build_context, Dqn_CPPBuildMode_AlwaysRebuild);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// NOTE: Feely Pona platform ===================================================================
|
// NOTE: Feely Pona platform ===================================================================
|
||||||
@ -419,10 +319,16 @@ int main()
|
|||||||
build_context.link_flags = feely_pona_no_dll_build_context.link_flags;
|
build_context.link_flags = feely_pona_no_dll_build_context.link_flags;
|
||||||
build_context.build_dir = build_dir;
|
build_context.build_dir = build_dir;
|
||||||
|
|
||||||
Dqn_CPPBuild_ExecuteOrAbort(build_context);
|
if (dry_run) {
|
||||||
|
Dqn_String8 cmd = Dqn_CPPBuild_ToCommandLine(build_context, Dqn_CPPBuildMode_AlwaysRebuild, scratch.allocator);
|
||||||
|
Dqn_Print_StdLnF(Dqn_PrintStd_Out, "%.*s\n", DQN_STRING_FMT(cmd));
|
||||||
|
} else {
|
||||||
|
Dqn_CPPBuild_ExecOrAbort(build_context, Dqn_CPPBuildMode_AlwaysRebuild);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Dqn_Print_StdLnF(Dqn_PrintStd_Out, "");
|
build_timings[1] = Dqn_OS_PerfCounterNow();
|
||||||
|
Dqn_Print_StdLnF(Dqn_PrintStd_Out, "\n-- Dqn_CPPBuild Timings (%.2fms)", Dqn_OS_PerfCounterMs(build_timings[0], build_timings[1]));
|
||||||
Dqn_Print_StdLnF(Dqn_PrintStd_Out, " robocopy: %.2fms", Dqn_OS_PerfCounterMs(robocopy_timings[0], robocopy_timings[1]));
|
Dqn_Print_StdLnF(Dqn_PrintStd_Out, " robocopy: %.2fms", Dqn_OS_PerfCounterMs(robocopy_timings[0], robocopy_timings[1]));
|
||||||
Dqn_Print_StdLnF(Dqn_PrintStd_Out, " raylib: %.2fms", Dqn_OS_PerfCounterMs(raylib_timings[0], raylib_timings[1]));
|
Dqn_Print_StdLnF(Dqn_PrintStd_Out, " raylib: %.2fms", Dqn_OS_PerfCounterMs(raylib_timings[0], raylib_timings[1]));
|
||||||
Dqn_Print_StdLnF(Dqn_PrintStd_Out, " feely pona sprite packer: %.2fms", Dqn_OS_PerfCounterMs(feely_pona_sprite_packer_timings[0], feely_pona_sprite_packer_timings[1]));
|
Dqn_Print_StdLnF(Dqn_PrintStd_Out, " feely pona sprite packer: %.2fms", Dqn_OS_PerfCounterMs(feely_pona_sprite_packer_timings[0], feely_pona_sprite_packer_timings[1]));
|
||||||
|
BIN
project.rdbg
BIN
project.rdbg
Binary file not shown.
Loading…
Reference in New Issue
Block a user