Subversion Repositories Kolibri OS

Rev

Rev 9325 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
9325 Boppan 1
#ifndef UMKA_H_INCLUDED
2
#define UMKA_H_INCLUDED
3
 
9337 Boppan 4
#include 
9325 Boppan 5
#include 
6
 
7
#define STDCALL __attribute__((__stdcall__))
8
 
9
#define BDFE_LEN_CP866 304
10
#define BDFE_LEN_UNICODE 560
11
 
12
typedef struct {
13
    uint32_t left, top, right, bottom;
14
} rect_t;
15
 
16
typedef struct {
17
    uint32_t left, top, width, height;
18
} box_t;
19
 
20
typedef struct {
21
    uint32_t dr0, dr1, dr2, dr3, dr7;
22
} dbg_regs_t;
23
 
24
typedef struct {
25
    uint32_t cpu_usage;
26
    uint16_t window_stack_position;
27
    uint16_t window_stack_value;
28
    uint16_t pad;
29
    char process_name[12];
30
    uint32_t memory_start;
31
    uint32_t used_memory;
32
    uint32_t pid;
33
    box_t box;
34
    uint16_t slot_state;
35
    uint16_t pad2;
36
    box_t client_box;
37
    uint8_t wnd_state;
38
    uint8_t pad3[1024-71];
39
} __attribute__((packed)) process_information_t;
40
 
41
_Static_assert(sizeof(process_information_t) == 0x400,
42
               "must be 0x400 bytes long");
43
 
44
typedef struct {
45
    box_t box;
46
    uint32_t cl_workarea;
47
    uint32_t cl_titlebar;
48
    uint32_t cl_frames;
49
    uint8_t z_modif;
50
    uint8_t fl_wstate;
51
    uint8_t fl_wdrawn;
52
    uint8_t fl_redraw;
53
} __attribute__((packed)) wdata_t;
54
 
55
_Static_assert(sizeof(wdata_t) == 0x20,
56
               "must be 0x20 bytes long");
57
 
58
typedef struct {
59
    uint32_t frame;
60
    uint32_t grab;
61
    uint32_t work_3d_dark;
62
    uint32_t work_3d_light;
63
    uint32_t grab_text;
64
    uint32_t work;
65
    uint32_t work_button;
66
    uint32_t work_button_text;
67
    uint32_t work_text;
68
    uint32_t work_graph;
69
} system_colors_t;
70
 
71
typedef enum {
72
    DEFAULT_ENCODING,
73
    CP866,
74
    UTF16,
75
    UTF8,
76
    INVALID_ENCODING,
77
} fs_enc_t;
78
 
79
typedef enum {
80
    F70 = 70,
81
    F80 = 80,
82
} f70or80_t;
83
 
84
enum {
85
    ERROR_SUCCESS,
86
    ERROR_DISK_BASE,
87
    ERROR_UNSUPPORTED_FS,
88
    ERROR_UNKNOWN_FS,
89
    ERROR_PARTITION,
90
    ERROR_FILE_NOT_FOUND,
91
    ERROR_END_OF_FILE,
92
    ERROR_MEMORY_POINTER,
93
    ERROR_DISK_FULL,
94
    ERROR_FS_FAIL,
95
    ERROR_ACCESS_DENIED,
96
    ERROR_DEVICE,
97
    ERROR_OUT_OF_MEMORY,
98
};
99
 
100
typedef struct lhead lhead_t;
101
 
102
struct lhead {
103
    lhead_t *next;
104
    lhead_t *prev;
105
};
106
 
107
typedef struct {
108
    lhead_t  wait_list;
109
    uint32_t count;
110
} mutex_t;
111
 
112
typedef mutex_t rwsem_t;
113
 
114
typedef struct {
115
    uint32_t flags;
116
    uint32_t sector_size;
117
    uint64_t capacity;  // in sectors
118
} diskmediainfo_t;
119
 
120
typedef struct {
121
    uintptr_t   pointer;
122
    uint32_t    data_size;
123
    uintptr_t   data;
124
    uint32_t    sad_size;
125
    uint32_t    search_start;
126
    uint32_t    sector_size_log;
127
} disk_cache_t;
128
 
129
typedef struct {
130
    uint64_t first_sector;
131
    uint64_t length;    // in sectors
132
    void *disk;
133
    void *fs_user_functions;
134
} partition_t;
135
 
136
typedef struct disk_t disk_t;
137
 
138
typedef struct {
139
    uint32_t  strucsize;
140
    STDCALL void (*close)(void *userdata);
141
    STDCALL void (*closemedia)(void *userdata);
142
    STDCALL int (*querymedia)(void *userdata, diskmediainfo_t *info);
143
    STDCALL int (*read)(void *userdata, void *buffer, off_t startsector,
144
                        size_t *numsectors);
145
    STDCALL int (*write)(void *userdata, void *buffer, off_t startsector,
146
                         size_t *numsectors);
147
    STDCALL int (*flush)(void *userdata);
148
    STDCALL unsigned int (*adjust_cache_size)(void *userdata,
149
                                              size_t suggested_size);
150
} diskfunc_t;
151
 
152
struct disk_t {
153
    disk_t *next;
154
    disk_t *prev;
155
    diskfunc_t *functions;
156
    const char *name;
157
    void *userdata;
158
    uint32_t driver_flags;
159
    uint32_t ref_count;
160
    mutex_t media_lock;
161
    uint8_t media_inserted;
162
    uint8_t media_used;
163
    uint16_t padding;
164
    uint32_t media_ref_count;
165
    diskmediainfo_t media_info;
166
    uint32_t num_partitions;
167
    partition_t **partitions;
168
    uint32_t cache_size;
169
    mutex_t cache_lock;
170
    disk_cache_t sys_cache;
171
    disk_cache_t app_cache;
172
};
173
 
174
typedef struct {
175
    uint32_t attr;
176
    uint32_t enc;
177
    uint32_t ctime;
178
    uint32_t cdate;
179
    uint32_t atime;
180
    uint32_t adate;
181
    uint32_t mtime;
182
    uint32_t mdate;
183
    uint64_t size;
184
    char name[0x7777];  // how to handle this properly? FIXME
185
} bdfe_t;
186
 
187
typedef struct {
188
    int32_t status;
189
    uint32_t count;
190
} f7080ret_t;
191
 
192
typedef struct {
193
    uint32_t sf;
194
    uint64_t offset;
195
    uint32_t count;
196
    void *buf;
197
    union {
198
        struct {
199
            uint8_t zero;
200
            const char *path;
201
        } __attribute__((packed)) f70;
202
        struct {
203
            uint32_t path_encoding;
204
            const char *path;
205
        } f80;
206
    } u;
207
} __attribute__((packed)) f7080s0arg_t;
208
 
209
typedef struct {
210
    uint32_t sf;
211
    uint32_t offset;
212
    uint32_t encoding;
213
    uint32_t size;
214
    void *buf;
215
    union {
216
        struct {
217
            uint8_t zero;
218
            const char *path;
219
        } __attribute__((packed)) f70;
220
        struct {
221
            uint32_t path_encoding;
222
            const char *path;
223
        } f80;
224
    } u;
225
} __attribute__((packed)) f7080s1arg_t;
226
 
227
typedef struct {
228
    uint32_t version;
229
    uint32_t cnt;
230
    uint32_t total_cnt;
231
    uint32_t zeroed[5];
232
    bdfe_t bdfes[];
233
} f7080s1info_t;
234
 
235
typedef struct {
236
    uint32_t sf;
237
    uint32_t reserved1;
238
    uint32_t flags;
239
    uint32_t reserved2;
240
    void *buf;
241
    union {
242
        struct {
243
            uint8_t zero;
244
            const char *path;
245
        } __attribute__((packed)) f70;
246
        struct {
247
            uint32_t path_encoding;
248
            const char *path;
249
        } f80;
250
    } u;
251
} __attribute__((packed)) f7080s5arg_t;
252
 
253
typedef struct {
254
    uint32_t sf;
255
    uint32_t flags;
256
    char *params;
257
    uint32_t reserved1;
258
    uint32_t reserved2;
259
    union {
260
        struct {
261
            uint8_t zero;
262
            const char *path;
263
        } __attribute__((packed)) f70;
264
        struct {
265
            uint32_t path_encoding;
266
            const char *path;
267
        } f80;
268
    } u;
269
} __attribute__((packed)) f7080s7arg_t;
270
 
271
#define KF_READONLY 0x01
272
#define KF_HIDDEN   0x02
273
#define KF_SYSTEM   0x04
274
#define KF_LABEL    0x08
275
#define KF_FOLDER   0x10
276
#define KF_ATTR_CNT 5
277
 
278
#define HASH_SIZE 32
279
typedef struct {
280
    uint8_t hash[HASH_SIZE];
281
    uint8_t opaque[1024-HASH_SIZE];
282
} hash_context;
283
 
284
typedef struct {
285
    uint32_t edi;
286
    uint32_t esi;
287
    uint32_t ebp;
288
    uint32_t esp;
289
    uint32_t ebx;
290
    uint32_t edx;
291
    uint32_t ecx;
292
    uint32_t eax;
293
} pushad_t;
294
 
295
#define NET_TYPE_ETH  1
296
#define NET_TYPE_SLIP 2
297
 
298
// Link state
299
#define ETH_LINK_DOWN    0x0    // Link is down
300
#define ETH_LINK_UNKNOWN 0x1    // There could be an active link
301
#define ETH_LINK_FD      0x2    // full duplex flag
302
#define ETH_LINK_10M     0x4    // 10 mbit
303
#define ETH_LINK_100M    0x8    // 100 mbit
304
#define ETH_LINK_1G      0xc    // gigabit
305
 
306
// Ethernet protocol numbers
307
#define ETHER_PROTO_ARP           0x0608
308
#define ETHER_PROTO_IPv4          0x0008
309
#define ETHER_PROTO_IPv6          0xDD86
310
#define ETHER_PROTO_PPP_DISCOVERY 0x6388
311
#define ETHER_PROTO_PPP_SESSION   0x6488
312
 
313
// Internet protocol numbers
314
#define IP_PROTO_IP   0
315
#define IP_PROTO_ICMP 1
316
#define IP_PROTO_TCP  6
317
#define IP_PROTO_UDP  17
318
#define IP_PROTO_RAW  255
319
 
320
// IP options
321
#define IP_TOS     1
322
#define IP_TTL     2
323
#define IP_HDRINCL 3
324
 
325
// PPP protocol numbers
326
#define PPP_PROTO_IPv4     0x2100
327
#define PPP_PROTO_IPV6     0x5780
328
#define PPP_PROTO_ETHERNET 666
329
 
330
// Protocol family
331
#define AF_INET4  AF_INET
332
 
333
typedef struct net_device_t net_device_t;
334
 
335
typedef struct {
336
        void *next;     // pointer to next frame in list
337
        void *prev;     // pointer to previous frame in list
338
        net_device_t *device;   // ptr to NET_DEVICE structure
339
        uint32_t type;  // encapsulation type: e.g. Ethernet
340
        size_t length;  // size of encapsulated data
341
        size_t offset;  // offset to actual data (24 bytes for default frame)
342
        uint8_t data[];
343
} net_buff_t;
344
 
345
struct net_device_t {
346
    uint32_t device_type;   // type field
347
    uint32_t mtu;           // Maximal Transmission Unit
348
    char *name;             // ptr to 0 terminated string
349
 
350
    // ptrs to driver functions
351
    STDCALL void (*unload) (void);
352
    STDCALL void (*reset) (void);
353
    STDCALL int (*transmit) (net_buff_t *);
354
 
355
    uint64_t bytes_tx;      // statistics, updated by the driver
356
    uint64_t bytes_rx;
357
    uint32_t packets_tx;
358
    uint32_t packets_rx;
359
 
360
    uint32_t link_state;    // link state (0 = no link)
361
    uint32_t hwacc;         // bitmask stating enabled HW accelerations (offload
362
                            // engines)
363
    uint8_t mac[6];
364
    void *userdata;         // not in kolibri, umka-specific
365
}; // NET_DEVICE
366
 
367
typedef struct {
368
    uint32_t ip;
369
    uint8_t mac[6];
370
    uint16_t status;
371
    uint16_t ttl;
372
} arp_entry_t;
373
 
374
typedef struct acpi_node acpi_node_t;
375
struct acpi_node {
376
    uint32_t name;
377
    int32_t refcount;
378
    acpi_node_t *parent;
379
    acpi_node_t *children;
380
    acpi_node_t *next;
381
    int32_t type;
382
};
383
 
384
typedef struct {
385
    acpi_node_t node;
386
    uint64_t value;
387
} kos_node_integer_t;
388
 
389
typedef struct {
390
    acpi_node_t node;
391
    acpi_node_t **list;
392
    size_t el_cnt;
393
} kos_node_package_t;
394
 
395
__attribute__((__noreturn__)) void
396
kos_osloop(void);
397
 
398
void
9337 Boppan 399
irq0(int signo, void *info_unused, void *context);
9325 Boppan 400
 
401
void
402
umka_init(void);
403
 
404
void
405
i40(void);
406
 
407
uint32_t
408
kos_time_to_epoch(uint32_t *time);
409
 
410
STDCALL disk_t *
411
disk_add(diskfunc_t *disk, const char *name, void *userdata, uint32_t flags);
412
 
413
STDCALL void *
414
disk_media_changed(diskfunc_t *disk, int inserted);
415
 
416
STDCALL void
417
disk_del(disk_t *disk);
418
 
419
void
420
hash_oneshot(void *ctx, void *data, size_t len);
421
 
422
extern uint8_t xfs_user_functions[];
423
extern uint8_t ext_user_functions[];
424
extern uint8_t fat_user_functions[];
425
extern uint8_t ntfs_user_functions[];
426
 
427
extern uint8_t kos_ramdisk[2880*512];
428
 
429
disk_t *
430
kos_ramdisk_init(void);
431
 
432
STDCALL void
433
kos_set_mouse_data(uint32_t btn_state, int32_t xmoving, int32_t ymoving,
434
                   int32_t vscroll, int32_t hscroll);
435
 
436
static inline void
437
umka_mouse_move(int lbheld, int mbheld, int rbheld, int xabs, int32_t xmoving,
438
                int yabs, int32_t ymoving, int32_t hscroll, int32_t vscroll) {
439
    uint32_t btn_state = lbheld + (rbheld << 1) + (mbheld << 2) +
440
                         (yabs << 30) + (xabs << 31);
441
    kos_set_mouse_data(btn_state, xmoving, ymoving, vscroll, hscroll);
442
}
443
 
444
STDCALL net_buff_t *
445
kos_net_buff_alloc(size_t size);
446
 
447
static inline size_t
448
umka_new_sys_threads(uint32_t flags, void (*entry)(), void *stack) {
449
    size_t tid;
450
    __asm__ __inline__ __volatile__ (
451
        "push ebx;"
452
        "push esi;"
453
        "push edi;"
454
        "call   kos_new_sys_threads;"
455
        "pop edi;"
456
        "pop esi;"
457
        "pop ebx"
458
        : "=a"(tid)
459
        : "b"(flags),
460
          "c"(entry),
461
          "d"(stack)
462
        : "memory", "cc");
463
    return tid;
464
}
465
 
466
static inline void
467
kos_acpi_call_name(void *ctx, const char *name) {
468
    __asm__ __inline__ __volatile__ (
469
        "pushad;"
470
        "push   %[name];"
471
        "push   %[ctx];"
472
        "call   acpi.call_name;"
473
        "popad"
474
        :
475
        : [ctx] "r"(ctx), [name] "r"(name)
476
        : "memory", "cc");
477
}
478
 
479
#define KOS_ACPI_NODE_Uninitialized 1
480
#define KOS_ACPI_NODE_Integer       2
481
#define KOS_ACPI_NODE_String        3
482
#define KOS_ACPI_NODE_Buffer        4
483
#define KOS_ACPI_NODE_Package       5
484
#define KOS_ACPI_NODE_OpRegionField 6
485
#define KOS_ACPI_NODE_IndexField    7
486
#define KOS_ACPI_NODE_BankField     8
487
#define KOS_ACPI_NODE_Device        9
488
 
489
extern acpi_node_t *kos_acpi_root;
490
 
491
typedef struct {
492
    int pew[0x100];
493
} amlctx_t;
494
 
495
struct pci_dev {
496
    struct pci_dev *next;
497
    size_t bus;
498
    size_t dev;
499
    size_t fun;
500
    void *acpi;
501
    struct pci_dev *children;
502
    struct pci_dev *parent;
503
    void *prt;
504
    size_t is_bridge;
505
    size_t vendor_id;
506
    size_t device_id;
507
    size_t int_pin;
508
    size_t gsi;
509
};
510
 
511
extern struct pci_dev *kos_pci_root;
512
 
513
void
514
kos_acpi_aml_init();
515
 
516
STDCALL void
517
kos_aml_attach(acpi_node_t *parent, acpi_node_t *node);
518
 
519
STDCALL void
520
kos_acpi_fill_pci_irqs(void *ctx);
521
 
522
STDCALL amlctx_t*
523
kos_acpi_aml_new_thread();
524
 
525
STDCALL acpi_node_t*
526
kos_aml_alloc_node(int32_t type);
527
 
528
STDCALL acpi_node_t*
529
kos_aml_constructor_integer(void);
530
 
531
STDCALL acpi_node_t*
532
kos_aml_constructor_package(size_t el_cnt);
533
 
534
STDCALL acpi_node_t*
535
kos_acpi_lookup_node(acpi_node_t *root, char *name);
536
 
537
STDCALL void
538
kos_acpi_print_tree(void *ctx);
539
 
540
#define MAX_PCI_DEVICES 256
541
 
542
extern void *kos_acpi_dev_data;
543
extern size_t kos_acpi_dev_size;
544
extern void *kos_acpi_dev_next;
545
 
546
STDCALL void*
547
kos_kernel_alloc(size_t len);
548
 
549
STDCALL void
550
kos_pci_walk_tree(struct pci_dev *node,
551
                  STDCALL void* (*test)(struct pci_dev *node, void *arg),
552
                  STDCALL void* (*clbk)(struct pci_dev *node, void *arg),
553
                  void *arg);
554
 
555
typedef struct {
556
    uint32_t value;
557
    uint32_t errorcode;
558
} f75ret_t;
559
 
560
typedef struct {
561
    uint32_t eax;
562
    uint32_t ebx;
563
} f76ret_t;
564
 
565
static inline void
566
umka_stack_init() {
567
    __asm__ __inline__ __volatile__ (
568
        "pushad;"
569
        "call   kos_stack_init;"
570
        "popad"
571
        :
572
        :
573
        : "memory", "cc");
574
}
575
 
576
static inline int32_t
577
kos_net_add_device(net_device_t *dev) {
578
    int32_t dev_num;
579
    __asm__ __inline__ __volatile__ (
580
        "call   net_add_device"
581
        : "=a"(dev_num)
582
        : "b"(dev)
583
        : "ecx", "edx", "esi", "edi", "memory", "cc");
584
 
585
    return dev_num;
586
}
587
 
588
STDCALL void
589
kos_window_set_screen(ssize_t left, ssize_t top, ssize_t right, ssize_t bottom,
590
                      ssize_t proc);
591
 
592
typedef struct {
593
    int32_t x;
594
    int32_t y;
595
    size_t width;
596
    size_t height;
597
    size_t bits_per_pixel;
598
    size_t vrefresh;
599
    void *current_lfb;
600
    size_t lfb_pitch;
601
 
602
    rwsem_t win_map_lock;
603
    uint8_t *win_map;
604
    size_t win_map_pitch;
605
    size_t win_map_size;
606
 
607
    void *modes;
608
    void *ddev;
609
    void *connector;
610
    void *crtc;
611
 
612
    void *cr_list_next;
613
    void *cr_list_prev;
614
 
615
    void *cursor;
616
 
617
    void *init_cursor;
618
    void *select_cursor;
619
    void *show_cursor;
620
    void *move_cursor;
621
    void *restore_cursor;
622
    void *disable_mouse;
623
    size_t mask_seqno;
624
    void *check_mouse;
625
    void *check_m_pixel;
626
 
627
    size_t bytes_per_pixel;
628
} __attribute__((packed)) display_t;
629
 
630
extern display_t kos_display;
631
 
632
typedef struct {
633
    uint64_t addr;
634
    uint64_t size;
635
    uint32_t type;
636
} e820entry_t;
637
 
638
#define MAX_MEMMAP_BLOCKS 32
639
 
640
typedef struct {
641
    uint8_t bpp;    // bits per pixel
642
    uint16_t pitch; // scanline length
643
    uint8_t pad1[5];
644
    uint16_t vesa_mode;
645
    uint16_t x_res;
646
    uint16_t y_res;
647
    uint8_t pad2[6];
648
    uint32_t bank_switch;   // Vesa 1.2 pm bank switch
649
    void *lfb;  // Vesa 2.0 LFB address
650
    uint8_t mtrr;   // 0 or 1: enable MTRR graphics acceleration
651
    uint8_t launcher_start; // 0 or 1: start the first app (right now it's
652
                            // LAUNCHER) after kernel is loaded
653
    uint8_t debug_print;    // if nonzero, duplicates debug output to the screen
654
    uint8_t dma;    // DMA write: 1=yes, 2=no
655
    uint8_t pci_data[8];
656
    uint8_t pad3[8];
657
    uint8_t shutdown_type;  // see sysfn 18.9
658
    uint8_t pad4[15];
659
    uint32_t apm_entry; // entry point of APM BIOS
660
    uint16_t apm_version;   // BCD
661
    uint16_t apm_flags;
662
    uint8_t pad5[8];
663
    uint16_t apm_code_32;
664
    uint16_t apm_code_16;
665
    uint16_t apm_data_16;
666
    uint8_t rd_load_from;   // Device to load ramdisk from, RD_LOAD_FROM_*
667
    uint8_t pad6[1];
668
    uint16_t kernel_restart;
669
    uint16_t sys_disk;  // Device to mount on /sys/, see loader_doc.txt for details
670
    void *acpi_rsdp;
671
    char syspath[0x17];
672
    void *devicesdat_data;
673
    size_t devicesdat_size;
674
    uint8_t bios_hd_cnt;    // number of BIOS hard disks
675
    uint8_t bios_hd[0x80];  // BIOS hard disks
676
    size_t memmap_block_cnt;    // available physical memory map: number of blocks
677
    e820entry_t memmap_blocks[MAX_MEMMAP_BLOCKS];
678
    uint8_t acpi_usage;
679
} __attribute__((packed)) boot_data_t;
680
 
681
extern boot_data_t kos_boot;
682
 
683
void
684
umka_cli(void);
685
 
686
void
687
umka_sti(void);
688
 
689
extern uint8_t coverage_begin[];
690
extern uint8_t coverage_end[];
691
 
692
typedef struct appobj_t appobj_t;
693
 
694
struct appobj_t {
695
    uint32_t magic;
696
    void *destroy;  // internal destructor
697
    appobj_t *fd;   // next object in list
698
    appobj_t *bk;   // prev object in list
699
    uint32_t pid;   // owner id
700
};
701
 
702
typedef struct {
703
    uint32_t magic;
704
    void *destroy;  // internal destructor
705
    appobj_t *fd;   // next object in list
706
    appobj_t *bk;   // prev object in list
707
    uint32_t pid;   // owner id
708
    uint32_t id;    // event uid
709
    uint32_t state; // internal flags
710
    uint32_t code;
711
    uint32_t pad[5];
712
} event_t;
713
 
714
typedef struct {
715
    lhead_t list;
716
    lhead_t thr_list;
717
    mutex_t heap_lock;
718
    void *heap_base;
719
    void *heap_top;
720
    uint32_t mem_used;
721
    void *dlls_list_ptr;
722
    void *pdt_0_phys;
723
    void *pdt_1_phys;
724
    void *io_map_0;
725
    void *io_map_1;
726
 
727
    void *ht_lock;
728
    void *ht_free;
729
    void *ht_next;
730
    void *htab[(1024-18*4)/4];
731
    void *pdt_0[1024];
732
} proc_t;
733
 
734
_Static_assert(sizeof(proc_t) == 0x1400, "must be 0x1400 bytes long");
735
 
736
typedef struct {
737
    char app_name[11];
738
    uint8_t pad1[5];
739
 
740
    lhead_t list;                  // +16
741
    proc_t *process;               // +24
742
    void *fpu_state;               // +28
743
    void *exc_handler;             // +32
744
    uint32_t except_mask;          // +36
745
    void *pl0_stack;               // +40
746
    void *cursor;                  // +44
747
    event_t *fd_ev;                // +48
748
    event_t *bk_ev;                // +52
749
    appobj_t *fd_obj;              // +56
750
    appobj_t *bk_obj;              // +60
751
    void *saved_esp;               // +64
752
    uint32_t io_map[2];            // +68
753
    uint32_t dbg_state;            // +76
754
    char *cur_dir;                 // +80
755
    uint32_t wait_timeout;         // +84
756
    uint32_t saved_esp0;           // +88
757
    uint32_t wait_begin;           // +92
758
    int (*wait_test)(void);        // +96
759
    void *wait_param;              // +100
760
    void *tls_base;                // +104
761
    uint32_t event_mask;           // +108
762
    uint32_t tid;                  // +112
763
    uint32_t draw_bgr_x;           // +116
764
    uint32_t draw_bgr_y;           // +120
765
    uint8_t state;                 // +124
766
    uint8_t pad2[3];               // +125
767
    uint8_t *wnd_shape;            // +128
768
    uint32_t wnd_shape_scale;      // +132
769
    uint32_t mem_start;            // +136
770
    uint32_t counter_sum;          // +140
771
    box_t saved_box;               // +144
772
    uint32_t *ipc_start;           // +160
773
    size_t ipc_size;               // +164
774
    uint32_t occurred_events;      // +168
775
    uint32_t debugger_slot;        // +172
776
    uint32_t terminate_protection; // +176
777
    uint8_t keyboard_mode;         // +180
778
    uint8_t captionEncoding;       // +181
779
    uint8_t pad3[2];               // +182
780
    char *exec_params;             // +184
781
    void *dbg_event_mem;           // +188
782
    dbg_regs_t dbg_regs;           // +192
783
    char *wnd_caption;             // +212
784
    box_t wnd_clientbox;           // +216
785
    uint32_t priority;             // +232
786
    lhead_t in_schedule;           // +236
787
    uint32_t counter_add;          // +244
788
    uint32_t cpu_usage;            // +248
789
    uint32_t pad4;                 // +252
790
} appdata_t;
791
 
792
_Static_assert(sizeof(appdata_t) == 256, "must be 0x100 bytes long");
793
 
794
typedef struct {
795
    uint32_t event_mask;
796
    uint32_t pid;
797
    uint16_t pad1;
798
    uint8_t state;
799
    uint8_t pad2;
800
    uint16_t pad3;
801
    uint8_t wnd_number;
802
    uint8_t pad4;
803
    uint32_t mem_start;
804
    uint32_t counter_sum;
805
    uint32_t counter_add;
806
    uint32_t cpu_usage;
807
} taskdata_t;
808
 
809
_Static_assert(sizeof(taskdata_t) == 32, "must be 0x20 bytes long");
810
 
811
#define UMKA_SHELL 1u
812
#define UMKA_FUSE  2u
813
#define UMKA_OS    3u
814
 
815
#define MAX_PRIORITY    0 // highest, used for kernel tasks
816
#define USER_PRIORITY   1 // default
817
#define IDLE_PRIORITY   2 // lowest, only IDLE thread goes here
818
#define NR_SCHED_QUEUES 3 // MUST equal IDLE_PRIORYTY + 1
819
 
820
extern appdata_t *kos_scheduler_current[NR_SCHED_QUEUES];
821
 
822
extern uint32_t umka_tool;
823
extern uint32_t umka_initialized;
824
extern uint8_t kos_redraw_background;
825
extern size_t kos_task_count;
826
extern taskdata_t *kos_task_base;
827
extern wdata_t kos_window_data[];
828
extern taskdata_t kos_task_table[];
829
extern appdata_t kos_slot_base[];
830
extern uint32_t kos_current_process;
831
extern appdata_t *kos_current_slot;
832
extern uint32_t kos_current_slot_idx;
833
extern void umka_do_change_task(appdata_t *new);
834
extern void scheduler_add_thread(void);
835
extern void find_next_task(void);
836
extern uint8_t kos_lfb_base[];
837
extern uint16_t kos_win_stack[];
838
extern uint16_t kos_win_pos[];
839
extern uint32_t kos_acpi_ssdt_cnt;
840
extern uint8_t *kos_acpi_ssdt_base[];
841
extern size_t kos_acpi_ssdt_size[];
842
extern void *acpi_ctx;
843
extern uint32_t kos_acpi_usage;
844
extern uint32_t kos_acpi_node_alloc_cnt;
845
extern uint32_t kos_acpi_node_free_cnt;
846
extern uint32_t kos_acpi_count_nodes(void *ctx) STDCALL;
847
extern disk_t disk_list;
848
 
849
static inline void
850
umka_scheduler_add_thread(appdata_t *thread, int32_t priority) {
851
    __asm__ __inline__ __volatile__ (
852
        "call   do_change_thread"
853
        :
854
        : "c"(priority),
855
          "d"(thread)
856
        : "memory", "cc");
857
 
858
}
859
 
860
#define MAX_PRIORITY    0
861
#define USER_PRIORITY   1
862
#define IDLE_PRIORITY   2
863
#define NR_SCHED_QUEUES 3
864
 
865
#define SCHEDULE_ANY_PRIORITY 0
866
#define SCHEDULE_HIGHER_PRIORITY 1
867
 
868
typedef struct {
869
    appdata_t *appdata;
870
    taskdata_t *taskdata;
871
    int same;
872
} find_next_task_t;
873
 
874
static inline find_next_task_t
875
umka_find_next_task(int32_t priority) {
876
    find_next_task_t fnt;
877
    __asm__ __inline__ __volatile__ (
878
        "call   find_next_task;"
879
        "setz   al;"
880
        "movzx  eax, al"
881
        : "=b"(fnt.appdata),
882
          "=D"(fnt.taskdata),
883
          "=a"(fnt.same)
884
        : "b"(priority)
885
        : "memory", "cc");
886
    return fnt;
887
}
888
 
889
static inline void
890
umka_i40(pushad_t *regs) {
891
    __asm__ __inline__ __volatile__ (
892
        "push   ebp;"
893
        "mov    ebp, %[ebp];"
894
        "call   i40;"
895
        "pop    ebp"
896
        : "=a"(regs->eax),
897
          "=b"(regs->ebx)
898
        : "a"(regs->eax),
899
          "b"(regs->ebx),
900
          "c"(regs->ecx),
901
          "d"(regs->edx),
902
          "S"(regs->esi),
903
          "D"(regs->edi),
904
          [ebp] "Rm"(regs->ebp)
905
        : "memory");
906
}
907
 
908
static inline void
909
umka_sys_draw_window(size_t x, size_t xsize, size_t y, size_t ysize,
910
                     uint32_t color, int has_caption, int client_relative,
911
                     int fill_workarea, int gradient_fill, int movable,
912
                     uint32_t style, const char *caption) {
913
    __asm__ __inline__ __volatile__ (
914
        "call   i40"
915
        :
916
        : "a"(0),
917
          "b"((x << 16) + xsize),
918
          "c"((y << 16) + ysize),
919
          "d"((gradient_fill << 31) + (!fill_workarea << 30)
920
              + (client_relative << 29) + (has_caption << 28) + (style << 24)
921
              + color),
922
          "S"(!movable << 24),
923
          "D"(caption)
924
        : "memory");
925
}
926
 
927
static inline void
928
umka_sys_set_pixel(size_t x, size_t y, uint32_t color, int invert) {
929
    __asm__ __inline__ __volatile__ (
930
        "call   i40"
931
        :
932
        : "a"(1),
933
          "b"(x),
934
          "c"(y),
935
          "d"((invert << 24) + color)
936
        : "memory");
937
}
938
 
939
static inline void
940
umka_sys_write_text(size_t x, size_t y, uint32_t color, int asciiz,
941
                    int fill_background, int font_and_encoding,
942
                    int draw_to_buffer, int scale_factor, const char *string,
943
                    size_t length, uintptr_t background_color_or_buffer) {
944
    __asm__ __inline__ __volatile__ (
945
        "call   i40"
946
        :
947
        : "a"(4),
948
          "b"((x << 16) + y),
949
          "c"((asciiz << 31) + (fill_background << 30)
950
              + (font_and_encoding << 28) + (draw_to_buffer << 27)
951
              + (scale_factor << 24) + color),
952
          "d"(string),
953
          "S"(length),
954
          "D"(background_color_or_buffer)
955
        : "memory");
956
}
957
 
958
static inline void
959
umka_sys_put_image(void *image, size_t xsize, size_t ysize, size_t x,
960
                   size_t y) {
961
    __asm__ __inline__ __volatile__ (
962
        "call   i40"
963
        :
964
        : "a"(7),
965
          "b"(image),
966
          "c"((xsize << 16) + ysize),
967
          "d"((x << 16) + y)
968
        : "memory");
969
}
970
 
971
static inline void
972
umka_sys_button(size_t x, size_t xsize, size_t y, size_t ysize,
973
                size_t button_id, int draw_button, int draw_frame,
974
                uint32_t color) {
975
    __asm__ __inline__ __volatile__ (
976
        "call   i40"
977
        :
978
        : "a"(8),
979
          "b"((x << 16) + xsize),
980
          "c"((y << 16) + ysize),
981
          "d"((!draw_button << 30) + (!draw_frame << 29) + button_id),
982
          "S"(color)
983
        : "memory");
984
}
985
 
986
static inline void
987
umka_sys_process_info(int32_t pid, void *param) {
988
    __asm__ __inline__ __volatile__ (
989
        "call   i40"
990
        :
991
        : "a"(9),
992
          "b"(param),
993
          "c"(pid)
994
        : "memory");
995
}
996
 
997
static inline void
998
umka_sys_window_redraw(int begin_end) {
999
    __asm__ __inline__ __volatile__ (
1000
        "call   i40"
1001
        :
1002
        : "a"(12),
1003
          "b"(begin_end)
1004
        : "memory");
1005
}
1006
 
1007
static inline void
1008
umka_sys_draw_rect(size_t x, size_t xsize, size_t y, size_t ysize,
1009
                   uint32_t color, int gradient) {
1010
    __asm__ __inline__ __volatile__ (
1011
        "call   i40"
1012
        :
1013
        : "a"(13),
1014
          "b"((x << 16) + xsize),
1015
          "c"((y << 16) + ysize),
1016
          "d"((gradient << 31) + color)
1017
        : "memory");
1018
}
1019
 
1020
static inline void
1021
umka_sys_get_screen_size(uint32_t *xsize, uint32_t *ysize) {
1022
    uint32_t xysize;
1023
    __asm__ __inline__ __volatile__ (
1024
        "call   i40"
1025
        : "=a"(xysize)
1026
        : "a"(14)
1027
        : "memory");
1028
    *xsize = (xysize >> 16) + 1;
1029
    *ysize = (xysize & 0xffffu) + 1;
1030
}
1031
 
1032
static inline void
1033
umka_sys_bg_set_size(uint32_t xsize, uint32_t ysize) {
1034
    __asm__ __inline__ __volatile__ (
1035
        "call   i40"
1036
        :
1037
        : "a"(15),
1038
          "b"(1),
1039
          "c"(xsize),
1040
          "d"(ysize)
1041
        : "memory");
1042
}
1043
 
1044
static inline void
1045
umka_sys_bg_put_pixel(uint32_t offset, uint32_t color) {
1046
    __asm__ __inline__ __volatile__ (
1047
        "call   i40"
1048
        :
1049
        : "a"(15),
1050
          "b"(2),
1051
          "c"(offset),
1052
          "d"(color)
1053
        : "memory");
1054
}
1055
 
1056
static inline void
1057
umka_sys_bg_redraw() {
1058
    __asm__ __inline__ __volatile__ (
1059
        "call   i40"
1060
        :
1061
        : "a"(15),
1062
          "b"(3)
1063
        : "memory");
1064
}
1065
 
1066
static inline void
1067
umka_sys_bg_set_mode(uint32_t mode) {
1068
    __asm__ __inline__ __volatile__ (
1069
        "call   i40"
1070
        :
1071
        : "a"(15),
1072
          "b"(4),
1073
          "c"(mode)
1074
        : "memory");
1075
}
1076
 
1077
static inline void
1078
umka_sys_bg_put_img(void *image, size_t offset, size_t size) {
1079
    __asm__ __inline__ __volatile__ (
1080
        "call   i40"
1081
        :
1082
        : "a"(15),
1083
          "b"(5),
1084
          "c"(image),
1085
          "d"(offset),
1086
          "S"(size)
1087
        : "memory");
1088
}
1089
 
1090
static inline void *
1091
umka_sys_bg_map() {
1092
    void *addr;
1093
    __asm__ __inline__ __volatile__ (
1094
        "call   i40"
1095
        : "=a"(addr)
1096
        : "a"(15),
1097
          "b"(6)
1098
        : "memory");
1099
    return addr;
1100
}
1101
 
1102
static inline uint32_t
1103
umka_sys_bg_unmap(void *addr) {
1104
    uint32_t status;
1105
    __asm__ __inline__ __volatile__ (
1106
        "call   i40"
1107
        : "=a"(status)
1108
        : "a"(15),
1109
          "b"(7),
1110
          "c"(addr)
1111
        : "memory");
1112
    return status;
1113
}
1114
 
1115
static inline void
1116
umka_sys_set_cwd(const char *dir) {
1117
    __asm__ __inline__ __volatile__ (
1118
        "call   i40"
1119
        :
1120
        : "a"(30),
1121
          "b"(1),
1122
          "c"(dir)
1123
        : "memory");
1124
}
1125
 
1126
static inline void
1127
umka_sys_get_cwd(const char *buf, size_t len) {
1128
    __asm__ __inline__ __volatile__ (
1129
        "call   i40"
1130
        :
1131
        : "a"(30),
1132
          "b"(2),
1133
          "c"(buf),
1134
          "d"(len)
1135
        : "memory");
1136
}
1137
 
1138
static inline void
1139
umka_sys_draw_line(size_t x, size_t xend, size_t y, size_t yend, uint32_t color,
1140
                   int invert) {
1141
    __asm__ __inline__ __volatile__ (
1142
        "call   i40"
1143
        :
1144
        : "a"(38),
1145
          "b"((x << 16) + xend),
1146
          "c"((y << 16) + yend),
1147
          "d"((invert << 24) + color)
1148
        : "memory");
1149
}
1150
 
1151
static inline void
1152
umka_sys_display_number(int is_pointer, int base, int digits_to_display,
1153
                        int is_qword, int show_leading_zeros,
1154
                        int number_or_pointer, size_t x, size_t y,
1155
                        uint32_t color, int fill_background, int font,
1156
                        int draw_to_buffer, int scale_factor,
1157
                        uintptr_t background_color_or_buffer) {
1158
    __asm__ __inline__ __volatile__ (
1159
        "call   i40"
1160
        :
1161
        : "a"(47),
1162
          "b"(is_pointer + (base << 8) + (digits_to_display << 16)
1163
              + (is_qword << 30) + (show_leading_zeros << 31)),
1164
          "c"(number_or_pointer),
1165
          "d"((x << 16) + y),
1166
          "S"(color + (fill_background << 30) + (font << 28)
1167
              + (draw_to_buffer << 27) + (scale_factor << 24)),
1168
          "D"(background_color_or_buffer)
1169
        : "memory");
1170
}
1171
 
1172
static inline void
1173
umka_sys_set_button_style(int style) {
1174
    __asm__ __inline__ __volatile__ (
1175
        "call   i40"
1176
        :
1177
        : "a"(48),
1178
          "b"(1),
1179
          "c"(style)
1180
        : "memory");
1181
}
1182
 
1183
static inline void
1184
umka_sys_set_window_colors(void *colors) {
1185
    __asm__ __inline__ __volatile__ (
1186
        "call   i40"
1187
        :
1188
        : "a"(48),
1189
          "b"(2),
1190
          "c"(colors),
1191
          "d"(40)
1192
        : "memory");
1193
}
1194
 
1195
static inline void
1196
umka_sys_get_window_colors(void *colors) {
1197
    __asm__ __inline__ __volatile__ (
1198
        "call   i40"
1199
        :
1200
        : "a"(48),
1201
          "b"(3),
1202
          "c"(colors),
1203
          "d"(40)
1204
        : "memory");
1205
}
1206
 
1207
static inline uint32_t
1208
umka_sys_get_skin_height() {
1209
    uint32_t skin_height;
1210
    __asm__ __inline__ __volatile__ (
1211
        "call   i40"
1212
        : "=a"(skin_height)
1213
        : "a"(48),
1214
          "b"(4)
1215
        : "memory");
1216
    return skin_height;
1217
}
1218
 
1219
static inline void
1220
umka_sys_get_screen_area(rect_t *wa) {
1221
    uint32_t eax, ebx;
1222
    __asm__ __inline__ __volatile__ (
1223
        "call   i40"
1224
        : "=a"(eax),
1225
          "=b"(ebx)
1226
        : "a"(48),
1227
          "b"(5)
1228
        : "memory");
1229
    wa->left   = eax >> 16;
1230
    wa->right  = eax & 0xffffu;
1231
    wa->top    = ebx >> 16;
1232
    wa->bottom = ebx & 0xffffu;
1233
}
1234
 
1235
static inline void
1236
umka_sys_set_screen_area(rect_t *wa) {
1237
    uint32_t ecx, edx;
1238
    ecx = (wa->left << 16) + wa->right;
1239
    edx = (wa->top << 16) + wa->bottom;
1240
    __asm__ __inline__ __volatile__ (
1241
        "call   i40"
1242
        :
1243
        : "a"(48),
1244
          "b"(6),
1245
          "c"(ecx),
1246
          "d"(edx)
1247
        : "memory");
1248
}
1249
 
1250
static inline void
1251
umka_sys_get_skin_margins(rect_t *wa) {
1252
    uint32_t eax, ebx;
1253
    __asm__ __inline__ __volatile__ (
1254
        "call   i40"
1255
        : "=a"(eax),
1256
          "=b"(ebx)
1257
        : "a"(48),
1258
          "b"(7)
1259
        : "memory");
1260
    wa->left   = eax >> 16;
1261
    wa->right  = eax & 0xffffu;
1262
    wa->top    = ebx >> 16;
1263
    wa->bottom = ebx & 0xffffu;
1264
}
1265
 
1266
static inline int32_t
1267
umka_sys_set_skin(const char *path) {
1268
    int32_t status;
1269
    __asm__ __inline__ __volatile__ (
1270
        "call   i40"
1271
        : "=a"(status)
1272
        : "a"(48),
1273
          "b"(8),
1274
          "c"(path)
1275
        : "memory");
1276
    return status;
1277
}
1278
 
1279
static inline int
1280
umka_sys_get_font_smoothing() {
1281
    int type;
1282
    __asm__ __inline__ __volatile__ (
1283
        "call   i40"
1284
        : "=a"(type)
1285
        : "a"(48),
1286
          "b"(9)
1287
        : "memory");
1288
    return type;
1289
}
1290
 
1291
static inline void
1292
umka_sys_set_font_smoothing(int type) {
1293
    __asm__ __inline__ __volatile__ (
1294
        "call   i40"
1295
        :
1296
        : "a"(48),
1297
          "b"(10),
1298
          "c"(type)
1299
        : "memory");
1300
}
1301
 
1302
static inline int
1303
umka_sys_get_font_size() {
1304
    uint32_t size;
1305
    __asm__ __inline__ __volatile__ (
1306
        "call   i40"
1307
        : "=a"(size)
1308
        : "a"(48),
1309
          "b"(11)
1310
        : "memory");
1311
    return size;
1312
}
1313
 
1314
static inline void
1315
umka_sys_set_font_size(uint32_t size) {
1316
    __asm__ __inline__ __volatile__ (
1317
        "call   i40"
1318
        :
1319
        : "a"(48),
1320
          "b"(12),
1321
          "c"(size)
1322
        : "memory");
1323
}
1324
 
1325
static inline void
1326
umka_sys_put_image_palette(void *image, size_t xsize, size_t ysize,
1327
                           size_t x, size_t y, size_t bpp, void *palette,
1328
                           size_t row_offset) {
1329
    __asm__ __inline__ __volatile__ (
1330
        "push   ebp;"
1331
        "mov    ebp, %[row_offset];"
1332
        "call   i40;"
1333
        "pop    ebp"
1334
        :
1335
        : "a"(65),
1336
          "b"(image),
1337
          "c"((xsize << 16) + ysize),
1338
          "d"((x << 16) + y),
1339
          "S"(bpp),
1340
          "D"(palette),
1341
          [row_offset] "Rm"(row_offset)
1342
        : "memory");
1343
}
1344
 
1345
static inline void
1346
umka_sys_move_window(size_t x, size_t y, ssize_t xsize, ssize_t ysize) {
1347
    __asm__ __inline__ __volatile__ (
1348
        "call   i40"
1349
        :
1350
        : "a"(67),
1351
          "b"(x),
1352
          "c"(y),
1353
          "d"(xsize),
1354
          "S"(ysize)
1355
        : "memory");
1356
}
1357
 
1358
static inline void
1359
umka_sys_lfn(void *f7080sXarg, f7080ret_t *r, f70or80_t f70or80) {
1360
    __asm__ __inline__ __volatile__ (
1361
        "call   i40"
1362
        : "=a"(r->status),
1363
          "=b" (r->count)
1364
        : "a"(f70or80),
1365
          "b"(f7080sXarg)
1366
        : "memory");
1367
}
1368
 
1369
static inline void
1370
umka_sys_set_window_caption(const char *caption, int encoding) {
1371
    __asm__ __inline__ __volatile__ (
1372
        "call   i40"
1373
        :
1374
        : "a"(71),
1375
          "b"(encoding ? 2 : 1),
1376
          "c"(caption),
1377
          "d"(encoding)
1378
        : "memory");
1379
}
1380
 
1381
static inline void
1382
umka_sys_blit_bitmap(int operation, int background, int transparent,
1383
                     int client_relative, void *params) {
1384
    __asm__ __inline__ __volatile__ (
1385
        "call   i40"
1386
        :
1387
        : "a"(73),
1388
          "b"((client_relative << 29) + (transparent << 5) + (background << 4)
1389
              + operation),
1390
          "c"(params)
1391
        : "memory");
1392
}
1393
 
1394
static inline uint32_t
1395
umka_sys_net_get_dev_count() {
1396
    uint32_t count;
1397
    __asm__ __inline__ __volatile__ (
1398
        "call   i40"
1399
        : "=a"(count)
1400
        : "a"(74),
1401
          "b"(255)
1402
        : "memory");
1403
    return count;
1404
}
1405
 
1406
static inline int32_t
1407
umka_sys_net_get_dev_type(uint8_t dev_num) {
1408
    int32_t type;
1409
    __asm__ __inline__ __volatile__ (
1410
        "call   i40"
1411
        : "=a"(type)
1412
        : "a"(74),
1413
          "b"((dev_num << 8) + 0)
1414
        : "memory");
1415
    return type;
1416
}
1417
 
1418
static inline int32_t
1419
umka_sys_net_get_dev_name(uint8_t dev_num, char *name) {
1420
    int32_t status;
1421
    __asm__ __inline__ __volatile__ (
1422
        "call   i40"
1423
        : "=a"(status)
1424
        : "a"(74),
1425
          "b"((dev_num << 8) + 1),
1426
          "c"(name)
1427
        : "memory");
1428
    return status;
1429
}
1430
 
1431
static inline int32_t
1432
umka_sys_net_dev_reset(uint8_t dev_num) {
1433
    int32_t status;
1434
    __asm__ __inline__ __volatile__ (
1435
        "call   i40"
1436
        : "=a"(status)
1437
        : "a"(74),
1438
          "b"((dev_num << 8) + 2)
1439
        : "memory");
1440
    return status;
1441
}
1442
 
1443
static inline int32_t
1444
umka_sys_net_dev_stop(uint8_t dev_num) {
1445
    int32_t status;
1446
    __asm__ __inline__ __volatile__ (
1447
        "call   i40"
1448
        : "=a"(status)
1449
        : "a"(74),
1450
          "b"((dev_num << 8) + 3)
1451
        : "memory");
1452
    return status;
1453
}
1454
 
1455
static inline intptr_t
1456
umka_sys_net_get_dev(uint8_t dev_num) {
1457
    intptr_t dev;
1458
    __asm__ __inline__ __volatile__ (
1459
        "call   i40"
1460
        : "=a"(dev)
1461
        : "a"(74),
1462
          "b"((dev_num << 8) + 4)
1463
        : "memory");
1464
    return dev;
1465
}
1466
 
1467
static inline uint32_t
1468
umka_sys_net_get_packet_tx_count(uint8_t dev_num) {
1469
    uint32_t count;
1470
    __asm__ __inline__ __volatile__ (
1471
        "call   i40"
1472
        : "=a"(count)
1473
        : "a"(74),
1474
          "b"((dev_num << 8) + 6)
1475
        : "memory");
1476
    return count;
1477
}
1478
 
1479
static inline uint32_t
1480
umka_sys_net_get_packet_rx_count(uint8_t dev_num) {
1481
    uint32_t count;
1482
    __asm__ __inline__ __volatile__ (
1483
        "call   i40"
1484
        : "=a"(count)
1485
        : "a"(74),
1486
          "b"((dev_num << 8) + 7)
1487
        : "memory");
1488
    return count;
1489
}
1490
 
1491
static inline uint32_t
1492
umka_sys_net_get_byte_tx_count(uint8_t dev_num) {
1493
    uint32_t count;
1494
    __asm__ __inline__ __volatile__ (
1495
        "call   i40"
1496
        : "=a"(count)
1497
        : "a"(74),
1498
          "b"((dev_num << 8) + 8)
1499
        : "memory");
1500
    return count;
1501
}
1502
 
1503
static inline uint32_t
1504
umka_sys_net_get_byte_rx_count(uint8_t dev_num) {
1505
    uint32_t count;
1506
    __asm__ __inline__ __volatile__ (
1507
        "call   i40"
1508
        : "=a"(count)
1509
        : "a"(74),
1510
          "b"((dev_num << 8) + 9)
1511
        : "memory");
1512
    return count;
1513
}
1514
 
1515
static inline uint32_t
1516
umka_sys_net_get_link_status(uint8_t dev_num) {
1517
    uint32_t status;
1518
    __asm__ __inline__ __volatile__ (
1519
        "call   i40"
1520
        : "=a"(status)
1521
        : "a"(74),
1522
          "b"((dev_num << 8) + 10)
1523
        : "memory");
1524
    return status;
1525
}
1526
 
1527
static inline f75ret_t
1528
umka_sys_net_open_socket(uint32_t domain, uint32_t type, uint32_t protocol) {
1529
    f75ret_t r;
1530
    __asm__ __inline__ __volatile__ (
1531
        "call   i40"
1532
        : "=a"(r.value),
1533
          "=b"(r.errorcode)
1534
        : "a"(75),
1535
          "b"(0),
1536
          "c"(domain),
1537
          "d"(type),
1538
          "S"(protocol)
1539
        : "memory");
1540
    return r;
1541
}
1542
 
1543
static inline f75ret_t
1544
umka_sys_net_close_socket(uint32_t fd) {
1545
    f75ret_t r;
1546
    __asm__ __inline__ __volatile__ (
1547
        "call   i40"
1548
        : "=a"(r.value),
1549
          "=b"(r.errorcode)
1550
        : "a"(75),
1551
          "b"(1),
1552
          "c"(fd)
1553
        : "memory");
1554
    return r;
1555
}
1556
 
1557
static inline f75ret_t
1558
umka_sys_net_bind(uint32_t fd, void *sockaddr, size_t sockaddr_len) {
1559
    f75ret_t r;
1560
    __asm__ __inline__ __volatile__ (
1561
        "call   i40"
1562
        : "=a"(r.value),
1563
          "=b"(r.errorcode)
1564
        : "a"(75),
1565
          "b"(2),
1566
          "c"(fd),
1567
          "d"(sockaddr),
1568
          "S"(sockaddr_len)
1569
        : "memory");
1570
    return r;
1571
}
1572
 
1573
static inline f75ret_t
1574
umka_sys_net_listen(uint32_t fd, uint32_t backlog) {
1575
    f75ret_t r;
1576
    __asm__ __inline__ __volatile__ (
1577
        "call   i40"
1578
        : "=a"(r.value),
1579
          "=b"(r.errorcode)
1580
        : "a"(75),
1581
          "b"(3),
1582
          "c"(fd),
1583
          "d"(backlog)
1584
        : "memory");
1585
    return r;
1586
}
1587
 
1588
static inline f75ret_t
1589
umka_sys_net_connect(uint32_t fd, void *sockaddr, size_t sockaddr_len) {
1590
    f75ret_t r;
1591
    __asm__ __inline__ __volatile__ (
1592
        "call   i40"
1593
        : "=a"(r.value),
1594
          "=b"(r.errorcode)
1595
        : "a"(75),
1596
          "b"(4),
1597
          "c"(fd),
1598
          "d"(sockaddr),
1599
          "S"(sockaddr_len)
1600
        : "memory");
1601
    return r;
1602
}
1603
 
1604
static inline f75ret_t
1605
umka_sys_net_accept(uint32_t fd, void *sockaddr, size_t sockaddr_len) {
1606
    f75ret_t r;
1607
    __asm__ __inline__ __volatile__ (
1608
        "call   i40"
1609
        : "=a"(r.value),
1610
          "=b"(r.errorcode)
1611
        : "a"(75),
1612
          "b"(5),
1613
          "c"(fd),
1614
          "d"(sockaddr),
1615
          "S"(sockaddr_len)
1616
        : "memory");
1617
    return r;
1618
}
1619
 
1620
static inline f75ret_t
1621
umka_sys_net_send(uint32_t fd, void *buf, size_t buf_len, uint32_t flags) {
1622
    f75ret_t r;
1623
    __asm__ __inline__ __volatile__ (
1624
        "call   i40"
1625
        : "=a"(r.value),
1626
          "=b"(r.errorcode)
1627
        : "a"(75),
1628
          "b"(6),
1629
          "c"(fd),
1630
          "d"(buf),
1631
          "S"(buf_len),
1632
          "D"(flags)
1633
        : "memory");
1634
    return r;
1635
}
1636
 
1637
static inline f75ret_t
1638
umka_sys_net_receive(uint32_t fd, void *buf, size_t buf_len, uint32_t flags) {
1639
    f75ret_t r;
1640
    __asm__ __inline__ __volatile__ (
1641
        "call   i40"
1642
        : "=a"(r.value),
1643
          "=b"(r.errorcode)
1644
        : "a"(75),
1645
          "b"(7),
1646
          "c"(fd),
1647
          "d"(buf),
1648
          "S"(buf_len),
1649
          "D"(flags)
1650
        : "memory");
1651
    return r;
1652
}
1653
 
1654
static inline f76ret_t
1655
umka_sys_net_eth_read_mac(uint32_t dev_num) {
1656
    f76ret_t r;
1657
    __asm__ __inline__ __volatile__ (
1658
        "call   i40"
1659
        : "=a"(r.eax),
1660
          "=b"(r.ebx)
1661
        : "a"(76),
1662
          "b"((0 << 16) + (dev_num << 8) + 0)
1663
        : "memory");
1664
    return r;
1665
}
1666
 
1667
// Function 76, Protocol 1 - IPv4, Subfunction 0, Read # Packets sent =
1668
// Function 76, Protocol 1 - IPv4, Subfunction 1, Read # Packets rcvd =
1669
 
1670
static inline f76ret_t
1671
umka_sys_net_ipv4_get_addr(uint32_t dev_num) {
1672
    f76ret_t r;
1673
    __asm__ __inline__ __volatile__ (
1674
        "call   i40"
1675
        : "=a"(r.eax),
1676
          "=b"(r.ebx)
1677
        : "a"(76),
1678
          "b"((1 << 16) + (dev_num << 8) + 2)
1679
        : "memory");
1680
    return r;
1681
}
1682
 
1683
static inline f76ret_t
1684
umka_sys_net_ipv4_set_addr(uint32_t dev_num, uint32_t addr) {
1685
    f76ret_t r;
1686
    __asm__ __inline__ __volatile__ (
1687
        "call   i40"
1688
        : "=a"(r.eax),
1689
          "=b"(r.ebx)
1690
        : "a"(76),
1691
          "b"((1 << 16) + (dev_num << 8) + 3),
1692
          "c"(addr)
1693
        : "memory");
1694
    return r;
1695
}
1696
 
1697
static inline f76ret_t
1698
umka_sys_net_ipv4_get_dns(uint32_t dev_num) {
1699
    f76ret_t r;
1700
    __asm__ __inline__ __volatile__ (
1701
        "call   i40"
1702
        : "=a"(r.eax),
1703
          "=b"(r.ebx)
1704
        : "a"(76),
1705
          "b"((1 << 16) + (dev_num << 8) + 4)
1706
        : "memory");
1707
    return r;
1708
}
1709
 
1710
static inline f76ret_t
1711
umka_sys_net_ipv4_set_dns(uint32_t dev_num, uint32_t dns) {
1712
    f76ret_t r;
1713
    __asm__ __inline__ __volatile__ (
1714
        "call   i40"
1715
        : "=a"(r.eax),
1716
          "=b"(r.ebx)
1717
        : "a"(76),
1718
          "b"((1 << 16) + (dev_num << 8) + 5),
1719
          "c"(dns)
1720
        : "memory");
1721
    return r;
1722
}
1723
 
1724
static inline f76ret_t
1725
umka_sys_net_ipv4_get_subnet(uint32_t dev_num) {
1726
    f76ret_t r;
1727
    __asm__ __inline__ __volatile__ (
1728
        "call   i40"
1729
        : "=a"(r.eax),
1730
          "=b"(r.ebx)
1731
        : "a"(76),
1732
          "b"((1 << 16) + (dev_num << 8) + 6)
1733
        : "memory");
1734
    return r;
1735
}
1736
 
1737
static inline f76ret_t
1738
umka_sys_net_ipv4_set_subnet(uint32_t dev_num, uint32_t subnet) {
1739
    f76ret_t r;
1740
    __asm__ __inline__ __volatile__ (
1741
        "call   i40"
1742
        : "=a"(r.eax),
1743
          "=b"(r.ebx)
1744
        : "a"(76),
1745
          "b"((1 << 16) + (dev_num << 8) + 7),
1746
          "c"(subnet)
1747
        : "memory");
1748
    return r;
1749
}
1750
 
1751
static inline f76ret_t
1752
umka_sys_net_ipv4_get_gw(uint32_t dev_num) {
1753
    f76ret_t r;
1754
    __asm__ __inline__ __volatile__ (
1755
        "call   i40"
1756
        : "=a"(r.eax),
1757
          "=b"(r.ebx)
1758
        : "a"(76),
1759
          "b"((1 << 16) + (dev_num << 8) + 8)
1760
        : "memory");
1761
    return r;
1762
}
1763
 
1764
static inline f76ret_t
1765
umka_sys_net_ipv4_set_gw(uint32_t dev_num, uint32_t gw) {
1766
    f76ret_t r;
1767
    __asm__ __inline__ __volatile__ (
1768
        "call   i40"
1769
        : "=a"(r.eax),
1770
          "=b"(r.ebx)
1771
        : "a"(76),
1772
          "b"((1 << 16) + (dev_num << 8) + 9),
1773
          "c"(gw)
1774
        : "memory");
1775
    return r;
1776
}
1777
 
1778
// Function 76, Protocol 2 - ICMP, Subfunction 0, Read # Packets sent =
1779
// Function 76, Protocol 2 - ICMP, Subfunction 1, Read # Packets rcvd =
1780
// Function 76, Protocol 3 - UDP, Subfunction 0, Read # Packets sent ==
1781
// Function 76, Protocol 3 - UDP, Subfunction 1, Read # Packets rcvd ==
1782
// Function 76, Protocol 4 - TCP, Subfunction 0, Read # Packets sent ==
1783
// Function 76, Protocol 4 - TCP, Subfunction 1, Read # Packets rcvd ==
1784
// Function 76, Protocol 5 - ARP, Subfunction 0, Read # Packets sent ==
1785
// Function 76, Protocol 5 - ARP, Subfunction 1, Read # Packets rcvd ==
1786
static inline f76ret_t
1787
umka_sys_net_arp_get_count(uint32_t dev_num) {
1788
    f76ret_t r;
1789
    __asm__ __inline__ __volatile__ (
1790
        "call   i40"
1791
        : "=a"(r.eax),
1792
          "=b"(r.ebx)
1793
        : "a"(76),
1794
          "b"((5 << 16) + (dev_num << 8) + 2)
1795
        : "memory");
1796
    return r;
1797
}
1798
 
1799
static inline f76ret_t
1800
umka_sys_net_arp_get_entry(uint32_t dev_num, uint32_t arp_num, void *buf) {
1801
    f76ret_t r;
1802
    __asm__ __inline__ __volatile__ (
1803
        "call   i40"
1804
        : "=a"(r.eax),
1805
          "=b"(r.ebx)
1806
        : "a"(76),
1807
          "b"((5 << 16) + (dev_num << 8) + 3),
1808
          "c"(arp_num),
1809
          "D"(buf)
1810
        : "memory");
1811
    return r;
1812
}
1813
 
1814
static inline f76ret_t
1815
umka_sys_net_arp_add_entry(uint32_t dev_num, void *buf) {
1816
    f76ret_t r;
1817
    __asm__ __inline__ __volatile__ (
1818
        "call   i40"
1819
        : "=a"(r.eax),
1820
          "=b"(r.ebx)
1821
        : "a"(76),
1822
          "b"((5 << 16) + (dev_num << 8) + 4),
1823
          "S"(buf)
1824
        : "memory");
1825
    return r;
1826
}
1827
 
1828
static inline f76ret_t
1829
umka_sys_net_arp_del_entry(uint32_t dev_num, int32_t arp_num) {
1830
    f76ret_t r;
1831
    __asm__ __inline__ __volatile__ (
1832
        "call   i40"
1833
        : "=a"(r.eax),
1834
          "=b"(r.ebx)
1835
        : "a"(76),
1836
          "b"((5 << 16) + (dev_num << 8) + 5),
1837
          "c"(arp_num)
1838
        : "memory");
1839
    return r;
1840
}
1841
 
1842
// Function 76, Protocol 5 - ARP, Subfunction 6, Send ARP announce ==
1843
// Function 76, Protocol 5 - ARP, Subfunction 7, Read # conflicts ===
1844
 
1845
#endif  // UMKA_H_INCLUDED