This commit is contained in:
James 2024-03-26 16:31:37 +10:00
parent f84f21ae9d
commit 7cf190e692
7 changed files with 187 additions and 2 deletions

View File

@ -111,7 +111,10 @@ PUR_OBJS= \
build$(PS)main.obj \ build$(PS)main.obj \
build$(PS)error.obj \ build$(PS)error.obj \
build$(PS)stats.obj \ build$(PS)stats.obj \
build$(PS)systray.obj build$(PS)systray.obj \
build$(PS)ms_sleep.obj \
build$(PS)taskmgr.obj \
build$(PS)userpaths.obj
build$(PS)main.obj: build Makefile main.c api.h include$(PS)SDL.h include$(PS)SDL_image.h build$(PS)main.obj: build Makefile main.c api.h include$(PS)SDL.h include$(PS)SDL_image.h
$(CCOBJ) main.c $(OBJOUT)$@ $(CCOBJ) main.c $(OBJOUT)$@
@ -121,6 +124,12 @@ build$(PS)error.obj: build Makefile api.h error.c
$(CCOBJ) error.c $(OBJOUT)$@ $(CCOBJ) error.c $(OBJOUT)$@
build$(PS)systray.obj: build pf.ico pf.png api.h tray$(PS)tray.h build$(PS)systray.obj: build pf.ico pf.png api.h tray$(PS)tray.h
$(CCOBJ) systray.c $(OBJOUT)$@ $(CCOBJ) systray.c $(OBJOUT)$@
build$(PS)ms_sleep.obj: build ms_sleep.c
$(CCOBJ) ms_sleep.c $(OBJOUT)$@
build$(PS)taskmgr.obj: build api.h taskmgr.c
$(CCOBJ) taskmgr.c $(OBJOUT)$@
build$(PS)userpaths.obj: build api.h userpaths.c
$(CCOBJ) userpaths.c $(OBJOUT)$@
build: build:
mkdir build mkdir build

18
api.h
View File

@ -1,8 +1,26 @@
#ifndef api_h #ifndef api_h
#define api_h #define api_h
extern int app_is_live;
#include <stdarg.h> #include <stdarg.h>
void reportError(const char *fmt,...); void reportError(const char *fmt,...);
enum ps { ps_startup,ps_shutdown}; enum ps { ps_startup,ps_shutdown};
void print_stats(enum ps ps); void print_stats(enum ps ps);
unsigned taskmgr_ms_till_next(void);
void taskmgr_run(unsigned for_max_ms);
void ms_sleep(unsigned ms);
/**designed for relative time keeping, not recommended for use for absolute times*/
unsigned gettime_ms(void);
const char * get_config_file_path(void);
const char * get_app_dir(void);
int path_exists(const char *folder_or_file_path);
void make_dir(const char *folderpath);
#endif//api_h #endif//api_h

11
main.c
View File

@ -6,6 +6,8 @@
#include "api.h" #include "api.h"
int app_is_live=0;
SDL_Window * purrwin; SDL_Window * purrwin;
void purrer(void) { void purrer(void) {
SDL_Init(SDL_INIT_TIMER|SDL_INIT_EVENTS|SDL_INIT_VIDEO); SDL_Init(SDL_INIT_TIMER|SDL_INIT_EVENTS|SDL_INIT_VIDEO);
@ -20,10 +22,17 @@ void purrer(void) {
SDL_Quit(); SDL_Quit();
} }
int main(int argc,char**argv){ int main(int argc,char**argv){
app_is_live=1;
puts("hello world"); puts("hello world");
SDL_SetMainReady(); SDL_SetMainReady();
print_stats(ps_startup); print_stats(ps_startup);
purrer(); systray_initialscan();
//purrer();
while(app_is_live) {
unsigned ms_to_next_run = taskmgr_ms_till_next();
ms_sleep(ms_to_next_run);
taskmgr_run(0);
}
print_stats(ps_shutdown); print_stats(ps_shutdown);
return 0; return 0;
} }

14
ms_sleep.c Normal file
View File

@ -0,0 +1,14 @@
#ifdef _MSC_VER
#include <Windows.h>
void ms_sleep(unsigned ms) {
Sleep(ms);
}
unsigned gettime_ms(void){
SYSTEMTIME st;
FILETIME ft={0,0};
GetSystemTime(&st);
SystemTimeToFileTime(&st,&ft);
return ft.dwLowDateTime;
}
#endif

View File

@ -1,4 +1,22 @@
#include <stdio.h>
#include "tray/tray.h" #include "tray/tray.h"
#include "api.h" #include "api.h"
void systray_initialscan(void){
FILE *cfg;
if(!path_exists(get_app_dir())){
/*--create directory--*/
make_dir(get_app_dir());
}
/*--load list of tracked files--*/
cfg = fopen(get_config_file_path(),"rb");
if(!cfg) {
perror(get_config_file_path());
return;
}
fclose(cfg);
}

92
taskmgr.c Normal file
View File

@ -0,0 +1,92 @@
#include "api.h"
#ifndef TASKMGR_MAX_TASKS
#define TASKMGR_MAX_TASKS 12
#endif
unsigned taskmgr_ms_till_next(void){
return 10;
}
static unsigned right_here=0;
struct run_tag {
int oneshot;/**<if true, free slot after first use (so setTimeout() rather than setInterval() basically)*/
int stack_up;/**<if true, run multiple times (max once per taskmgr_run() though) to catch up if we fall behind, else it is like dropframes*/
unsigned frequency_ms;
unsigned awaiting;/**<countdown*/
void(*cb)(void*ud);/**< this not being null means in use, if null, slot is free*/
void*ud;
char brief_descr[15+1];
unsigned deficit;/**<deposit left over change during stack_up logic*/
};
static unsigned time_passed(unsigned before,unsigned now){
unsigned timepassed=0;
if(now<before) {
timepassed = 0xfffffffful - before;
before=0;
}
timepassed += now-before;
return timepassed;
}
static struct run_tag run_tab[TASKMGR_MAX_TASKS];
/**@return true if there are stacked/immidiates left*/
static int one_loop(unsigned for_max_ms){
unsigned right_now = gettime_ms();
unsigned passed=0;
int i;
unsigned effective_passed;
int backed_up=0;
if(for_max_ms==0)for_max_ms=0xfffffffful;//0 means run at least once no matter what
/*--calc time passed--*/
if(right_now < right_here) {
/*--wrap around--*/
passed = right_now + (0xfffffffful - right_here);
} else passed = right_now - right_here;
/*--process all slots (active/inactive), some might be awaiting==0 so even if passed==0, still run--*/
for(i=0;i<TASKMGR_MAX_TASKS;++i){
if(run_tab[i].cb == NULL)continue;
effective_passed= passed + run_tab[i].deficit;
if(run_tab[i].awaiting < effective_passed) {
void(*task2run)(void*)=run_tab[i].cb;
void *taskParam = run_tab[i].ud;
effective_passed -= run_tab[i].awaiting;
if(effective_passed > 0 && effective_passed < run_tab[i].frequency_ms) {
run_tab[i].awaiting = run_tab[i].frequency_ms - effective_passed;
} else if(effective_passed > 0) {
backed_up=1;
if(run_tab[i].stack_up) {
/*--stack up logic--*/
run_tab[i].awaiting=0;
run_tab[i].deficit = effective_passed - run_tab[i].frequency_ms;
} else {
run_tab[i].awaiting=0;
}
}
if(run_tab[i].oneshot) {
run_tab[i].cb = NULL;
run_tab[i].ud = NULL;
}
task2run(run_tab[i].ud);
} else {
run_tab[i].awaiting -= effective_passed;
}
/*--deal with SLOW,LONG running callbacks vs for_max_ms "run for" issue--*/
if(time_passed(right_now,gettime_ms())>for_max_ms)break;
}
return backed_up;
}
void taskmgr_run(unsigned for_max_ms){
unsigned total_passed=0;
unsigned initial_moment = gettime_ms();
int backed_up = one_loop(for_max_ms);
if(for_max_ms > 0) {
while(backed_up) {
total_passed=time_passed(initial_moment,gettime_ms());
if(total_passed>=for_max_ms) break;
backed_up=one_loop(total_passed < for_max_ms ? for_max_ms - total_passed : 1);
}
}
}

25
userpaths.c Normal file
View File

@ -0,0 +1,25 @@
#include <stdlib.h>
#include <string.h>
char servers_ini_buf[260+1];
char app_path_buf[260+1];
#ifdef _MSC_VER
#include <io.h>
const char * get_app_dir(void){
const char *appdata = getenv("APPDATA");
snprintf(app_path_buf,sizeof app_path_buf,"%s",appdata?appdata:".");
return app_path_buf;
}
const char * get_config_file_path(void){
snprintf(servers_ini_buf,sizeof servers_ini_buf,"%s\\purforce\\servers.ini",get_app_dir());
return servers_ini_buf;
}
int path_exists(const char *folder_or_file_path){
int ret = _access(folder_or_file_path,00);//Existence only
return ret==0;
}
void make_dir(const char *folderpath){
_mkdir(folderpath);
}
#endif