API type check :D

master
Allen Webster 2019-10-06 20:09:21 -07:00
parent 13e8c0aed4
commit 41a67e296d
19 changed files with 659 additions and 67 deletions

104
4ed_api_check.cpp Normal file
View File

@ -0,0 +1,104 @@
/*
* Mr. 4th Dimention - Allen Webster
*
* 06.10.2019
*
* Type checker that lists errors between two api parses.
*
*/
// TOP
#include "4coder_base_types.h"
#include "4coder_token.h"
#include "generated/lexer_cpp.h"
#include "4ed_api_definition.h"
#include "4coder_base_types.cpp"
#include "4coder_stringf.cpp"
#include "4coder_malloc_allocator.cpp"
#include "4coder_token.cpp"
#include "generated/lexer_cpp.cpp"
#include "4coder_file.cpp"
#include "4ed_api_definition.cpp"
#include "4ed_api_parser.cpp"
#include <stdio.h>
////////////////////////////////
function void
print_usage(void){
printf("usage: <script> <source-1> {<source-1>} : <source-2> {<source-2>}\n"
" source-1 : the authoritative/master api source file(s)\n"
" source-2 : the 'remote' api source file(s) to check against the master\n");
exit(1);
}
int
main(int argc, char **argv){
Arena arena = make_arena_malloc();
if (argc < 4){
print_usage();
}
API_Definition_List master_list = {};
API_Definition_List remote_list = {};
{
i32 i = 1;
for (;i < argc; i += 1){
char *file_name = argv[i];
if (string_match(SCu8(file_name), string_u8_litexpr(":"))){
i += 1;
break;
}
FILE *file = fopen(file_name, "rb");
if (file == 0){
printf("error: could not open input file: '%s'\n", file_name);
continue;
}
String_Const_u8 text = file_load_all(&arena, file);
fclose(file);
if (text.size > 0){
api_parse_source_add_to_list(&arena, SCu8(file_name), text, &master_list);
}
}
for (;i < argc; i += 1){
char *file_name = argv[i];
FILE *file = fopen(file_name, "rb");
if (file == 0){
printf("error: could not open input file: '%s'\n", file_name);
continue;
}
String_Const_u8 text = file_load_all(&arena, file);
fclose(file);
if (text.size > 0){
api_parse_source_add_to_list(&arena, SCu8(file_name), text, &remote_list);
}
}
}
if (master_list.count == 0){
printf("error: no apis in master list\n");
exit(1);
}
if (remote_list.count == 0){
printf("error: no apis in remote list\n");
exit(1);
}
List_String_Const_u8 errors = {};
api_list_check(&arena, &master_list, &remote_list, APICheck_ReportAll, &errors);
String_Const_u8 string = string_list_flatten(&arena, errors, StringFill_NullTerminate);
printf("%.*s", string_expand(string));
if (string.size > 0){
exit(1);
}
return(0);
}
// BOTTOM

View File

@ -17,20 +17,25 @@ begin_api(Arena *arena, char *name){
}
function API_Call*
api_call(Arena *arena, API_Definition *api, String_Const_u8 name, String_Const_u8 return_type){
api_call_with_location(Arena *arena, API_Definition *api, String_Const_u8 name, String_Const_u8 type,
String_Const_u8 location){
API_Call *call = push_array_zero(arena, API_Call, 1);
sll_queue_push(api->first, api->last, call);
api->count += 1;
call->name = name;
call->return_type = return_type;
call->return_type = type;
call->location_string = location;
return(call);
}
function API_Call*
api_call(Arena *arena, API_Definition *api, char *name, char *return_type){
return(api_call(arena, api, SCu8(name), SCu8(return_type)));
api_call_with_location(Arena *arena, API_Definition *api, char *name, char *type, char *location){
return(api_call_with_location(arena, api, SCu8(name), SCu8(type), SCu8(location)));
}
#define api_call(arena, api, name, type) \
api_call_with_location((arena), (api), (name), (type), file_name_line_number)
function API_Param*
api_param(Arena *arena, API_Call *call, char *type_name, char *name){
API_Param *param = push_array_zero(arena, API_Param, 1);
@ -47,7 +52,7 @@ api_set_param_list(API_Call *call, API_Param_List list){
}
function API_Definition*
api_get_api(Arena *arena, API_Definition_List *list, String_Const_u8 name){
api_get_api(API_Definition_List *list, String_Const_u8 name){
API_Definition *result = 0;
for (API_Definition *node = list->first;
node != 0;
@ -57,6 +62,12 @@ api_get_api(Arena *arena, API_Definition_List *list, String_Const_u8 name){
break;
}
}
return(result);
}
function API_Definition*
api_get_api(Arena *arena, API_Definition_List *list, String_Const_u8 name){
API_Definition *result = api_get_api(list, name);
if (result == 0){
result = push_array_zero(arena, API_Definition, 1);
sll_queue_push(list->first, list->last, result);
@ -66,6 +77,39 @@ api_get_api(Arena *arena, API_Definition_List *list, String_Const_u8 name){
return(result);
}
function API_Call*
api_get_call(API_Definition *api, String_Const_u8 name){
API_Call *result = 0;
for (API_Call *call = api->first;
call != 0;
call = call->next){
if (string_match(name, call->name)){
result = call;
break;
}
}
return(result);
}
function b32
api_call_match_sigs(API_Call *a, API_Call *b){
b32 result = false;
if (a->params.count == b->params.count &&
string_match(a->return_type, b->return_type)){
result = true;
for (API_Param *a_param = a->params.first, *b_param = b->params.first;
a_param != 0 && b_param != 0;
a_param = a_param->next, b_param = b_param->next){
if (!string_match(a_param->name, b_param->name) ||
!string_match(a_param->type_name, b_param->type_name)){
result = false;
break;
}
}
}
return(result);
}
////////////////////////////////
#if !defined(SKIP_STDIO)
@ -335,6 +379,142 @@ api_definition_generate_api_includes(Arena *arena, API_Definition *api, Generate
return(true);
}
////////////////////////////////
function void
api_definition_error(Arena *arena, List_String_Const_u8 *list,
char *e1, API_Call *c1, char *e2, API_Call *c2){
Assert(e1 != 0);
Assert(c1 != 0);
string_list_pushf(arena, list,
"%.*s error: %s '%.*s'",
string_expand(c1->location_string),
e1, string_expand(c1->name));
if (e2 != 0){
string_list_pushf(arena, list, " %s", e2);
if (c2 != 0){
string_list_pushf(arena, list, " '%.*s'", string_expand(c2->name));
}
}
string_list_push(arena, list, string_u8_litexpr("\n"));
if (c2 != 0){
string_list_push(arena, list, c2->location_string);
string_list_pushf(arena, list, " note: see declaration of '%.*s'\n", string_expand(c2->name));
}
}
function void
api_definition_error(Arena *arena, List_String_Const_u8 *list,
char *e1, API_Call *c1, char *e2){
api_definition_error(arena, list, e1, c1, e2, 0);
}
function void
api_definition_error(Arena *arena, List_String_Const_u8 *list,
char *e1, API_Call *c1){
api_definition_error(arena, list, e1, c1, 0, 0);
}
function void
api_definition_error(Arena *arena, List_String_Const_u8 *list,
char *e1, API_Definition *api1, char *e2){
Assert(e1 != 0);
Assert(api1 != 0);
string_list_pushf(arena, list, "error: %s '%.*s'",
e1, string_expand(api1->name));
if (e2 != 0){
string_list_pushf(arena, list, " %s", e2);
}
string_list_push(arena, list, string_u8_litexpr("\n"));
}
function void
api_definition_error(Arena *arena, List_String_Const_u8 *list,
char *e1, API_Definition *api1){
api_definition_error(arena, list, e1, api1, 0);
}
function void
api_definition_check(Arena *arena, API_Definition *correct, API_Definition *remote, API_Check_Flag flags, List_String_Const_u8 *error_list){
b32 report_missing = HasFlag(flags, APICheck_ReportMissingAPI);
b32 report_extra = HasFlag(flags, APICheck_ReportExtraAPI);
b32 report_mismatch = HasFlag(flags, APICheck_ReportMismatchAPI);
b32 iterate_correct = (report_missing || report_mismatch);
if (iterate_correct){
for (API_Call *call = correct->first;
call != 0;
call = call->next){
API_Call *remote_call = api_get_call(remote, call->name);
if (remote_call == 0 && report_missing){
api_definition_error(arena, error_list,
"no remote call for", call);
}
if (remote_call != 0 && !api_call_match_sigs(call, remote_call) && report_mismatch){
api_definition_error(arena, error_list,
"remote call", remote_call,
"does not match signature for", call);
}
}
}
b32 iterate_remote = (report_extra);
if (iterate_remote){
for (API_Call *call = remote->first;
call != 0;
call = call->next){
API_Call *correct_call = api_get_call(correct, call->name);
if (correct_call == 0 && report_extra){
api_definition_error(arena, error_list,
"remote call", call,
"does not exist in api master");
}
}
}
}
function void
api_list_check(Arena *arena, API_Definition_List *correct, API_Definition_List *remote, API_Check_Flag flags, List_String_Const_u8 *error_list){
b32 report_missing = HasFlag(flags, APICheck_ReportMissingAPI);
b32 report_extra = HasFlag(flags, APICheck_ReportExtraAPI);
b32 iterate_correct = (report_missing);
if (iterate_correct){
for (API_Definition *api = correct->first;
api != 0;
api = api->next){
API_Definition *remote_api = api_get_api(remote, api->name);
if (remote_api == 0 && report_missing){
api_definition_error(arena, error_list,
"no remote api for", api);
}
}
}
b32 iterate_remote = (report_extra);
if (iterate_remote){
for (API_Definition *api = remote->first;
api != 0;
api = api->next){
API_Definition *correct_api = api_get_api(correct, api->name);
if (correct_api == 0 && report_extra){
api_definition_error(arena, error_list,
"remote api", api,
"does not have a master");
}
}
}
for (API_Definition *api = correct->first;
api != 0;
api = api->next){
API_Definition *remote_api = api_get_api(remote, api->name);
if (remote_api != 0){
api_definition_check(arena, api, remote_api, flags, error_list);
}
}
}
#endif
// BOTTOM

View File

@ -28,6 +28,7 @@ struct API_Call{
API_Call *next;
String_Const_u8 name;
String_Const_u8 return_type;
String_Const_u8 location_string;
API_Param_List params;
};
@ -52,6 +53,16 @@ enum{
APIGeneration_NoAPINameOnCallables = 1,
};
typedef u32 API_Check_Flag;
enum{
APICheck_ReportMissingAPI = 1,
APICheck_ReportExtraAPI = 2,
APICheck_ReportMismatchAPI = 4,
};
enum{
APICheck_ReportAll = APICheck_ReportMissingAPI|APICheck_ReportExtraAPI|APICheck_ReportMismatchAPI,
};
#endif
// BOTTOM

View File

@ -9,21 +9,6 @@
// TOP
#include "4coder_base_types.h"
#include "4coder_token.h"
#include "generated/lexer_cpp.h"
#include "4ed_api_definition.h"
#include "4coder_base_types.cpp"
#include "4coder_stringf.cpp"
#include "4coder_malloc_allocator.cpp"
#include "4coder_token.cpp"
#include "generated/lexer_cpp.cpp"
#include "4coder_file.cpp"
#include "4ed_api_definition.cpp"
////////////////////////////////
/*
function:
api ( <identifier> ) function <identifier> {*} <identifier> ( <param_list> )
@ -103,15 +88,41 @@ api_parse_add_param(Arena *arena, API_Param_List *list, String_Const_u8 type, i3
}
function void
api_parse_add_function(Arena *arena, API_Definition_List *list, String_Const_u8 api_name, String_Const_u8 func_name, String_Const_u8 type, i32 star_counter, API_Param_List param_list){
api_parse_add_function(Arena *arena, API_Definition_List *list,
String_Const_u8 api_name, String_Const_u8 func_name,
String_Const_u8 type, i32 star_counter, API_Param_List param_list,
String_Const_u8 location){
API_Definition *api = api_get_api(arena, list, api_name);
type = api_parse__type_name_with_stars(arena, type, star_counter);
API_Call *call = api_call(arena, api, func_name, type);
API_Call *call = api_call_with_location(arena, api, func_name, type, location);
api_set_param_list(call, param_list);
}
function String_Const_u8
api_parse_location(Arena *arena, String_Const_u8 source_name, String_Const_u8 source, u8 *pos){
i32 line_number = 1;
i32 col_number = 1;
if (source.str <= pos && pos < source.str + source.size){
for (u8 *ptr = source.str;;){
if (ptr == pos){
break;
}
if (*ptr == '\n'){
line_number += 1;
col_number = 1;
}
else{
col_number += 1;
}
ptr += 1;
}
}
return(push_u8_stringf(arena, "%.*s:%d:%d:", string_expand(source_name), line_number, col_number));
}
function void
api_parse_source_add_to_list(Arena *arena, String_Const_u8 source, API_Definition_List *list){
api_parse_source_add_to_list(Arena *arena, String_Const_u8 source_name, String_Const_u8 source,
API_Definition_List *list){
Token_List token_list = lex_full_input_cpp(arena, source);
Token_Iterator token_it = token_iterator(token_iterator(0, &token_list));
@ -187,7 +198,10 @@ api_parse_source_add_to_list(Arena *arena, String_Const_u8 source, API_Definitio
}
if (success){
api_parse_add_function(arena, list, api_name, func_name, ret_type, ret_type_star_counter, param_list);
String_Const_u8 location = api_parse_location(arena, source_name, source, func_name.str);
api_parse_add_function(arena, list, api_name, func_name,
ret_type, ret_type_star_counter, param_list,
location);
}
}
else{
@ -196,50 +210,14 @@ api_parse_source_add_to_list(Arena *arena, String_Const_u8 source, API_Definitio
}
}
}
}
function API_Definition_List
api_parse_source(Arena *arena, String_Const_u8 source){
api_parse_source(Arena *arena, String_Const_u8 source_name, String_Const_u8 source){
API_Definition_List list = {};
api_parse_source_add_to_list(arena, source, &list);
api_parse_source_add_to_list(arena, source_name, source, &list);
return(list);
}
////////////////////////////////
int
main(int argc, char **argv){
Arena arena = make_arena_malloc();
if (argc < 2){
printf("usage: <script> <source> {<source>}\n"
" source : file to load and parse into the output list\n");
exit(1);
}
API_Definition_List list = {};
for (i32 i = 1; i < argc; i += 1){
FILE *file = fopen(argv[i], "rb");
if (file == 0){
printf("error: could not open input file: '%s'\n", argv[i]);
continue;
}
String_Const_u8 text = file_load_all(&arena, file);
fclose(file);
if (text.size > 0){
api_parse_source_add_to_list(&arena, text, &list);
}
}
for (API_Definition *node = list.first;
node != 0;
node = node->next){
api_definition_generate_api_includes(&arena, node, GeneratedGroup_Custom, APIGeneration_NoAPINameOnCallables);
}
}
// BOTTOM

64
4ed_api_parser_main.cpp Normal file
View File

@ -0,0 +1,64 @@
/*
* Mr. 4th Dimention - Allen Webster
*
* 06.10.2019
*
* Parser that extracts an API from C++ source code.
*
*/
// TOP
#include "4coder_base_types.h"
#include "4coder_token.h"
#include "generated/lexer_cpp.h"
#include "4ed_api_definition.h"
#include "4coder_base_types.cpp"
#include "4coder_stringf.cpp"
#include "4coder_malloc_allocator.cpp"
#include "4coder_token.cpp"
#include "generated/lexer_cpp.cpp"
#include "4coder_file.cpp"
#include "4ed_api_definition.cpp"
#include "4ed_api_parser.cpp"
#include <stdio.h>
////////////////////////////////
int
main(int argc, char **argv){
Arena arena = make_arena_malloc();
if (argc < 2){
printf("usage: <script> <source> {<source>}\n"
" source : file to load and parse into the output list\n");
exit(1);
}
API_Definition_List list = {};
for (i32 i = 1; i < argc; i += 1){
char *file_name = argv[i];
FILE *file = fopen(file_name, "rb");
if (file == 0){
printf("error: could not open input file: '%s'\n", argv[i]);
continue;
}
String_Const_u8 text = file_load_all(&arena, file);
fclose(file);
if (text.size > 0){
api_parse_source_add_to_list(&arena, SCu8(file_name), text, &list);
}
}
for (API_Definition *node = list.first;
node != 0;
node = node->next){
api_definition_generate_api_includes(&arena, node, GeneratedGroup_Custom, APIGeneration_NoAPINameOnCallables);
}
}
// BOTTOM

View File

@ -301,8 +301,8 @@ global_const f32 epsilon_f32 = 5.96046448e-8f;
#define clamp_unsigned_to_u32(x) (u32)(clamp_top((u64)(x), (u64)u32_max))
#define clamp_unsigned_to_u64(x) (u64)(clamp_top((u64)(x), (u64)u64_max))
#define LINE_STR stringify(__LINE__)
#define FNLN __FILE__ ":" LINE_STR ":"
#define LINE_STR__ stringify(__LINE__)
#define file_name_line_number __FILE__ ":" LINE_STR__ ":"
#define require(c) Stmnt( if (!(c)){ return(0); } )

View File

@ -0,0 +1,43 @@
api(system) function String_Const_u8 get_path(Arena* arena, System_Path_Code path_code);
api(system) function String_Const_u8 get_canonical(Arena* arena, String_Const_u8 name);
api(system) function File_List get_file_list(Arena* arena, String_Const_u8 directory);
api(system) function File_Attributes quick_file_attributes(Arena* scratch, String_Const_u8 file_name);
api(system) function b32 load_handle(Arena* scratch, char* file_name, Plat_Handle* out);
api(system) function File_Attributes load_attributes(Plat_Handle handle);
api(system) function b32 load_file(Plat_Handle handle, char* buffer, u32 size);
api(system) function b32 load_close(Plat_Handle handle);
api(system) function File_Attributes save_file(Arena* scratch, char* file_name, String_Const_u8 data);
api(system) function b32 load_library(Arena* scratch, String_Const_u8 file_name, System_Library* out);
api(system) function b32 release_library(System_Library handle);
api(system) function Void_Func* get_proc(System_Library handle, char* proc_name);
api(system) function u64 now_time(void);
api(system) function Plat_Handle wake_up_timer_create(void);
api(system) function void wake_up_timer_release(Plat_Handle handle);
api(system) function void wake_up_timer_set(Plat_Handle handle, u32 time_milliseconds);
api(system) function void signal_step(u32 code);
api(system) function void sleep(u64 microseconds);
api(system) function void post_clipboard(String_Const_u8 str);
api(system) function b32 cli_call(Arena* scratch, char* path, char* script, CLI_Handles* cli_out);
api(system) function void cli_begin_update(CLI_Handles* cli);
api(system) function b32 cli_update_step(CLI_Handles* cli, char* dest, u32 max, u32* amount);
api(system) function b32 cli_end_update(CLI_Handles* cli);
api(system) function void open_color_picker(Color_Picker* picker);
api(system) function f32 get_screen_scale_factor(void);
api(system) function System_Thread thread_launch(Thread_Function* proc, void* ptr);
api(system) function void thread_join(System_Thread thread);
api(system) function void thread_free(System_Thread thread);
api(system) function i32 thread_get_id(void);
api(system) function System_Mutex mutex_make(void);
api(system) function void mutex_acquire(System_Mutex mutex);
api(system) function void mutex_release(System_Mutex mutex);
api(system) function void mutex_free(System_Mutex mutex);
api(system) function System_Condition_Variable condition_variable_make(void);
api(system) function void condition_variable_wait(System_Condition_Variable cv, System_Mutex mutex);
api(system) function void condition_variable_signal(System_Condition_Variable cv);
api(system) function void condition_variable_free(System_Condition_Variable cv);
api(system) function void* memory_allocate(umem size);
api(system) function b32 memory_set_protection(void* ptr, umem size, u32 flags);
api(system) function void memory_free(void* ptr, umem size);
api(system) function void show_mouse_cursor(i32 show);
api(system) function b32 set_fullscreen(b32 full_screen);
api(system) function b32 is_fullscreen(void);

View File

@ -678,7 +678,7 @@ internal void
win32_init_gl(HDC hdc){
//LOG("trying to load wgl extensions...\n");
#define GLInitFail(s) system_error_box(FNLN "\nOpenGL init fail - " s )
#define GLInitFail(s) system_error_box(file_name_line_number "\nOpenGL init fail - " s )
// Init First Context
WNDCLASSA wglclass = {};

View File

@ -59,7 +59,11 @@ command_list = {
{ .name = "build api parser",
.out = "*compilation*", .footer_panel = true, .save_dirty_files = true,
.cmd = { { "custom\\bin\\build_one_time 4ed_api_parser.cpp ..\\build & copy /B ..\\build\\one_time.exe ..\\build\\api_parser.exe", .os = "win" }, }, },
.cmd = { { "custom\\bin\\build_one_time 4ed_api_parser_main.cpp ..\\build & copy /B ..\\build\\one_time.exe ..\\build\\api_parser.exe", .os = "win" }, }, },
{ .name = "build api checker",
.out = "*compilation*", .footer_panel = true, .save_dirty_files = true,
.cmd = { { "custom\\bin\\build_one_time 4ed_api_check.cpp ..\\build & copy /B ..\\build\\one_time.exe ..\\build\\api_checker.exe", .os = "win" }, }, },
{ .name = "generate custom api master list",
.out = "*run*", .footer_panel = false, .save_dirty_files = false,
@ -67,7 +71,7 @@ command_list = {
};
fkey_command[1] = "build x64";
fkey_command[2] = "build api parser";
fkey_command[2] = "build api checker";
fkey_command[4] = "run one time";
fkey_command[5] = "build C++ lexer generator";
fkey_command[6] = "build token tester";

View File

@ -0,0 +1,27 @@
mouse_xy 20 20
key P MDFR_CTRL
basewait 1
key o MDFR_CTRL
type 1 gentokentest1.cpp
key key_newline MDFR_NONE
key o MDFR_CTRL
key key_back MDFR_NONE
type 1 output/
key key_esc MDFR_NONE
key s MDFR_ALT
type 1 gentokentest1.cpp
key key_newline MDFR_NONE
key key_down MDFR_CTRL
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
key s MDFR_CTRL
exit
key Y MDFR_NONE

View File

@ -0,0 +1,27 @@
mouse_xy 20 20
key P MDFR_CTRL
basewait 1
key o MDFR_CTRL
type 1 gentokentest2.cpp
key key_newline MDFR_NONE
key o MDFR_CTRL
key key_back MDFR_NONE
type 1 output/
key key_esc MDFR_NONE
key s MDFR_ALT
type 1 gentokentest2.cpp
key key_newline MDFR_NONE
key key_down MDFR_CTRL
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
key s MDFR_CTRL
exit
key Y MDFR_NONE

View File

@ -0,0 +1,27 @@
mouse_xy 20 20
key P MDFR_CTRL
basewait 1
key o MDFR_CTRL
type 1 gentokentest3.cpp
key key_newline MDFR_NONE
key o MDFR_CTRL
key key_back MDFR_NONE
type 1 output/
key key_esc MDFR_NONE
key s MDFR_ALT
type 1 gentokentest3.cpp
key key_newline MDFR_NONE
key key_down MDFR_CTRL
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
key s MDFR_CTRL
exit
key Y MDFR_NONE

View File

@ -0,0 +1,27 @@
mouse_xy 20 20
key P MDFR_CTRL
basewait 1
key o MDFR_CTRL
type 1 gentokentest4.cpp
key key_newline MDFR_NONE
key o MDFR_CTRL
key key_back MDFR_NONE
type 1 output/
key key_esc MDFR_NONE
key s MDFR_ALT
type 1 gentokentest4.cpp
key key_newline MDFR_NONE
key key_down MDFR_CTRL
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
key s MDFR_CTRL
exit
key Y MDFR_NONE

View File

@ -0,0 +1,27 @@
mouse_xy 20 20
key P MDFR_CTRL
basewait 1
key o MDFR_CTRL
type 1 gentokentest5.cpp
key key_newline MDFR_NONE
key o MDFR_CTRL
key key_back MDFR_NONE
type 1 output/
key key_esc MDFR_NONE
key s MDFR_ALT
type 1 gentokentest5.cpp
key key_newline MDFR_NONE
key key_down MDFR_CTRL
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
type 1 int x = 0;
key key_newline MDFR_NONE
key s MDFR_CTRL
exit
key Y MDFR_NONE

View File

@ -0,0 +1,16 @@
mouse_xy 20 20
key P MDFR_CTRL
basewait 1
key o MDFR_CTRL
type 1 genduplinetest0_0.cpp
key key_newline MDFR_NONE
key o MDFR_CTRL
key key_back MDFR_NONE
type 1 output/
key key_esc MDFR_NONE
key s MDFR_ALT
type 1 genduplinetest0_0.cpp
key key_newline MDFR_NONE
key L MDFR_CTRL
key s MDFR_CTRL
exit

View File

@ -0,0 +1,16 @@
mouse_xy 20 20
key P MDFR_CTRL
basewait 1
key o MDFR_CTRL
type 1 genduplinetest0_1.cpp
key key_newline MDFR_NONE
key o MDFR_CTRL
key key_back MDFR_NONE
type 1 output/
key key_esc MDFR_NONE
key s MDFR_ALT
type 1 genduplinetest0_1.cpp
key key_newline MDFR_NONE
key L MDFR_CTRL
key s MDFR_CTRL
exit

View File

@ -0,0 +1,16 @@
mouse_xy 20 20
key P MDFR_CTRL
basewait 1
key o MDFR_CTRL
type 1 genduplinetest1_0.cpp
key key_newline MDFR_NONE
key o MDFR_CTRL
key key_back MDFR_NONE
type 1 output/
key key_esc MDFR_NONE
key s MDFR_ALT
type 1 genduplinetest1_0.cpp
key key_newline MDFR_NONE
key L MDFR_CTRL
key s MDFR_CTRL
exit

View File

@ -0,0 +1,16 @@
mouse_xy 20 20
key P MDFR_CTRL
basewait 1
key o MDFR_CTRL
type 1 genduplinetest1_1.cpp
key key_newline MDFR_NONE
key o MDFR_CTRL
key key_back MDFR_NONE
type 1 output/
key key_esc MDFR_NONE
key s MDFR_ALT
type 1 genduplinetest1_1.cpp
key key_newline MDFR_NONE
key L MDFR_CTRL
key s MDFR_CTRL
exit

View File

@ -0,0 +1,9 @@
mouse_xy 20 20
key P MDFR_CTRL
basewait 1
key i MDFR_CTRL
type 1 *messages*
key key_newline MDFR_NONE
key L MDFR_CTRL
key s MDFR_CTRL
exit