|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include <string.h>
|
|
#include <ctype.h>
|
|
#include <math.h>
|
|
#include <sys/socket.h>
|
|
#include <netinet/in.h>
|
|
#include <unistd.h>
|
|
#include <arpa/inet.h>
|
|
#include "types.h"
|
|
#include "native_functions.h"
|
|
#include "interpreter.h"
|
|
|
|
void register_native_func(char *name, NativeFunc func) {
|
|
if (!name || !func || native_func_cnt >= 100) {
|
|
return;
|
|
}
|
|
NativeFuncDef *nf = &native_funcs[native_func_cnt++];
|
|
strncpy(nf->name, name, 31);
|
|
nf->name[31] = 0;
|
|
nf->func = func;
|
|
}
|
|
|
|
long native_socket(long *args, int argc) {
|
|
if (!args || argc < 3) {
|
|
return -1;
|
|
}
|
|
int domain = (int)args[0];
|
|
int type = (int)args[1];
|
|
int protocol = (int)args[2];
|
|
return socket(domain, type, protocol);
|
|
}
|
|
|
|
long native_bind(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return -1;
|
|
}
|
|
int sockfd = (int)args[0];
|
|
int port = (int)args[1];
|
|
|
|
struct sockaddr_in addr;
|
|
memset(&addr, 0, sizeof(addr));
|
|
addr.sin_family = AF_INET;
|
|
addr.sin_addr.s_addr = INADDR_ANY;
|
|
addr.sin_port = htons(port);
|
|
|
|
return bind(sockfd, (struct sockaddr*)&addr, sizeof(addr));
|
|
}
|
|
|
|
long native_listen(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return -1;
|
|
}
|
|
int sockfd = (int)args[0];
|
|
int backlog = (int)args[1];
|
|
return listen(sockfd, backlog);
|
|
}
|
|
|
|
long native_accept(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return -1;
|
|
}
|
|
int sockfd = (int)args[0];
|
|
return accept(sockfd, NULL, NULL);
|
|
}
|
|
|
|
long native_recv(long *args, int argc) {
|
|
if (!args || argc < 4) {
|
|
return -1;
|
|
}
|
|
int sockfd = (int)args[0];
|
|
int addr = (int)args[1];
|
|
int len = (int)args[2];
|
|
int flags = (int)args[3];
|
|
|
|
if (addr < 0 || addr >= MEM_SIZE) {
|
|
return -1;
|
|
}
|
|
|
|
char temp_buf[8192];
|
|
if (len > 8192) len = 8192;
|
|
if (len < 0) len = 0;
|
|
|
|
if (addr + len > MEM_SIZE) {
|
|
len = MEM_SIZE - addr;
|
|
}
|
|
|
|
int result = recv(sockfd, temp_buf, len, flags);
|
|
if (result > 0) {
|
|
for (int i = 0; i < result && addr + i < MEM_SIZE; i++) {
|
|
memory[addr + i] = temp_buf[i];
|
|
}
|
|
}
|
|
return result;
|
|
}
|
|
|
|
long native_send(long *args, int argc) {
|
|
if (!args || argc < 4) {
|
|
return -1;
|
|
}
|
|
int sockfd = (int)args[0];
|
|
long buf_arg = args[1];
|
|
int len = (int)args[2];
|
|
int flags = (int)args[3];
|
|
|
|
if (len < 0) {
|
|
return -1;
|
|
}
|
|
|
|
if (buf_arg > MEM_SIZE * 8 || buf_arg < 0) {
|
|
return send(sockfd, (char*)buf_arg, len, flags);
|
|
}
|
|
|
|
if (buf_arg >= MEM_SIZE) {
|
|
return -1;
|
|
}
|
|
|
|
char temp_buf[8192];
|
|
if (len > 8192) len = 8192;
|
|
|
|
if (buf_arg + len > MEM_SIZE) {
|
|
len = MEM_SIZE - buf_arg;
|
|
}
|
|
|
|
for (int i = 0; i < len && buf_arg + i < MEM_SIZE; i++) {
|
|
temp_buf[i] = (char)memory[buf_arg + i];
|
|
}
|
|
|
|
return send(sockfd, temp_buf, len, flags);
|
|
}
|
|
|
|
long native_close(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return -1;
|
|
}
|
|
int fd = (int)args[0];
|
|
return close(fd);
|
|
}
|
|
|
|
long native_strlen(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return 0;
|
|
}
|
|
char *str = (char*)args[0];
|
|
if (!str) {
|
|
return 0;
|
|
}
|
|
return strlen(str);
|
|
}
|
|
|
|
long native_AF_INET(long *args, int argc) {
|
|
return AF_INET;
|
|
}
|
|
|
|
long native_SOCK_STREAM(long *args, int argc) {
|
|
return SOCK_STREAM;
|
|
}
|
|
|
|
long native_sqrt(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return 0;
|
|
}
|
|
return (long)sqrt((double)args[0]);
|
|
}
|
|
|
|
long native_pow(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return 0;
|
|
}
|
|
return (long)pow((double)args[0], (double)args[1]);
|
|
}
|
|
|
|
long native_sin(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return 0;
|
|
}
|
|
return (long)(sin((double)args[0]) * 1000000);
|
|
}
|
|
|
|
long native_cos(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return 0;
|
|
}
|
|
return (long)(cos((double)args[0]) * 1000000);
|
|
}
|
|
|
|
long native_tan(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return 0;
|
|
}
|
|
return (long)(tan((double)args[0]) * 1000000);
|
|
}
|
|
|
|
long native_abs(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return 0;
|
|
}
|
|
return (long)abs((int)args[0]);
|
|
}
|
|
|
|
long native_floor(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return 0;
|
|
}
|
|
return (long)floor((double)args[0]);
|
|
}
|
|
|
|
long native_ceil(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return 0;
|
|
}
|
|
return (long)ceil((double)args[0]);
|
|
}
|
|
|
|
long native_strpos(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return -1;
|
|
}
|
|
char *haystack = (char*)args[0];
|
|
char *needle = (char*)args[1];
|
|
if (!haystack || !needle) {
|
|
return -1;
|
|
}
|
|
char *pos = strstr(haystack, needle);
|
|
if (pos) {
|
|
return pos - haystack;
|
|
}
|
|
return -1;
|
|
}
|
|
|
|
long native_substr(long *args, int argc) {
|
|
static char empty_str[] = "";
|
|
if (!args || argc < 3) {
|
|
return (long)empty_str;
|
|
}
|
|
char *str = (char*)args[0];
|
|
if (!str) {
|
|
return (long)empty_str;
|
|
}
|
|
int start = (int)args[1];
|
|
int length = (int)args[2];
|
|
|
|
if (str_pool_idx >= STR_POOL_SIZE) {
|
|
error("String pool overflow");
|
|
return (long)empty_str;
|
|
}
|
|
|
|
char *result = &str_pool[str_pool_idx];
|
|
int str_len = strlen(str);
|
|
|
|
if (start < 0) start = 0;
|
|
if (start >= str_len) return (long)empty_str;
|
|
if (start + length > str_len) length = str_len - start;
|
|
if (length < 0) return (long)empty_str;
|
|
|
|
if (str_pool_idx + length + 1 >= STR_POOL_SIZE) {
|
|
error("String pool overflow");
|
|
return (long)empty_str;
|
|
}
|
|
|
|
strncpy(result, str + start, length);
|
|
result[length] = 0;
|
|
|
|
str_pool_idx += length + 1;
|
|
return (long)result;
|
|
}
|
|
|
|
long native_upper(long *args, int argc) {
|
|
static char empty_str[] = "";
|
|
if (!args || argc < 1) {
|
|
return (long)empty_str;
|
|
}
|
|
char *str = (char*)args[0];
|
|
if (!str) {
|
|
return (long)empty_str;
|
|
}
|
|
|
|
if (str_pool_idx >= STR_POOL_SIZE) {
|
|
error("String pool overflow");
|
|
return (long)empty_str;
|
|
}
|
|
|
|
char *result = &str_pool[str_pool_idx];
|
|
int len = strlen(str);
|
|
|
|
if (str_pool_idx + len + 1 >= STR_POOL_SIZE) {
|
|
error("String pool overflow");
|
|
return (long)empty_str;
|
|
}
|
|
|
|
for (int i = 0; i <= len; i++) {
|
|
result[i] = toupper(str[i]);
|
|
}
|
|
|
|
str_pool_idx += len + 1;
|
|
return (long)result;
|
|
}
|
|
|
|
long native_lower(long *args, int argc) {
|
|
static char empty_str[] = "";
|
|
if (!args || argc < 1) {
|
|
return (long)empty_str;
|
|
}
|
|
char *str = (char*)args[0];
|
|
if (!str) {
|
|
return (long)empty_str;
|
|
}
|
|
|
|
if (str_pool_idx >= STR_POOL_SIZE) {
|
|
error("String pool overflow");
|
|
return (long)empty_str;
|
|
}
|
|
|
|
char *result = &str_pool[str_pool_idx];
|
|
int len = strlen(str);
|
|
|
|
if (str_pool_idx + len + 1 >= STR_POOL_SIZE) {
|
|
error("String pool overflow");
|
|
return (long)empty_str;
|
|
}
|
|
|
|
for (int i = 0; i <= len; i++) {
|
|
result[i] = tolower(str[i]);
|
|
}
|
|
|
|
str_pool_idx += len + 1;
|
|
return (long)result;
|
|
}
|
|
|
|
long native_strip(long *args, int argc) {
|
|
static char empty_str[] = "";
|
|
if (!args || argc < 1) {
|
|
return (long)empty_str;
|
|
}
|
|
char *str = (char*)args[0];
|
|
if (!str) {
|
|
return (long)empty_str;
|
|
}
|
|
|
|
if (str_pool_idx >= STR_POOL_SIZE) {
|
|
error("String pool overflow");
|
|
return (long)empty_str;
|
|
}
|
|
|
|
char *result = &str_pool[str_pool_idx];
|
|
|
|
while (*str && isspace(*str)) str++;
|
|
|
|
int len = strlen(str);
|
|
while (len > 0 && isspace(str[len - 1])) len--;
|
|
|
|
if (str_pool_idx + len + 1 >= STR_POOL_SIZE) {
|
|
error("String pool overflow");
|
|
return (long)empty_str;
|
|
}
|
|
|
|
strncpy(result, str, len);
|
|
result[len] = 0;
|
|
|
|
str_pool_idx += len + 1;
|
|
return (long)result;
|
|
}
|
|
|
|
long native_replace(long *args, int argc) {
|
|
static char empty_str[] = "";
|
|
if (!args || argc < 3) {
|
|
return (long)empty_str;
|
|
}
|
|
char *str = (char*)args[0];
|
|
char *old_str = (char*)args[1];
|
|
char *new_str = (char*)args[2];
|
|
if (!str || !old_str || !new_str) {
|
|
return (long)empty_str;
|
|
}
|
|
|
|
if (str_pool_idx >= STR_POOL_SIZE) {
|
|
error("String pool overflow");
|
|
return (long)empty_str;
|
|
}
|
|
|
|
char *result = &str_pool[str_pool_idx];
|
|
char *src = str;
|
|
char *dst = result;
|
|
int old_len = strlen(old_str);
|
|
int new_len = strlen(new_str);
|
|
|
|
if (old_len == 0) {
|
|
int str_len = strlen(str);
|
|
if (str_pool_idx + str_len + 1 >= STR_POOL_SIZE) {
|
|
error("String pool overflow");
|
|
return (long)empty_str;
|
|
}
|
|
strcpy(result, str);
|
|
str_pool_idx += str_len + 1;
|
|
return (long)result;
|
|
}
|
|
|
|
while (*src) {
|
|
if (strncmp(src, old_str, old_len) == 0) {
|
|
int remaining = strlen(src + old_len);
|
|
int current_pos = dst - result;
|
|
if (str_pool_idx + current_pos + new_len + remaining + 1 >= STR_POOL_SIZE) {
|
|
error("String pool overflow");
|
|
*dst = 0;
|
|
str_pool_idx += current_pos + 1;
|
|
return (long)result;
|
|
}
|
|
strcpy(dst, new_str);
|
|
dst += new_len;
|
|
src += old_len;
|
|
} else {
|
|
*dst++ = *src++;
|
|
}
|
|
}
|
|
*dst = 0;
|
|
|
|
int total_len = dst - result;
|
|
str_pool_idx += total_len + 1;
|
|
return (long)result;
|
|
}
|
|
|
|
long native_startswith(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return 0;
|
|
}
|
|
char *str = (char*)args[0];
|
|
char *prefix = (char*)args[1];
|
|
if (!str || !prefix) {
|
|
return 0;
|
|
}
|
|
int prefix_len = strlen(prefix);
|
|
return strncmp(str, prefix, prefix_len) == 0;
|
|
}
|
|
|
|
long native_endswith(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return 0;
|
|
}
|
|
char *str = (char*)args[0];
|
|
char *suffix = (char*)args[1];
|
|
if (!str || !suffix) {
|
|
return 0;
|
|
}
|
|
int str_len = strlen(str);
|
|
int suffix_len = strlen(suffix);
|
|
|
|
if (suffix_len > str_len) return 0;
|
|
return strcmp(str + str_len - suffix_len, suffix) == 0;
|
|
}
|
|
|
|
long native_fopen(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return 0;
|
|
}
|
|
char *filename = (char*)args[0];
|
|
char *mode = (char*)args[1];
|
|
if (!filename || !mode) {
|
|
return 0;
|
|
}
|
|
FILE *f = fopen(filename, mode);
|
|
return (long)f;
|
|
}
|
|
|
|
long native_fclose(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return -1;
|
|
}
|
|
FILE *f = (FILE*)args[0];
|
|
if (!f) {
|
|
return -1;
|
|
}
|
|
return fclose(f);
|
|
}
|
|
|
|
long native_fread(long *args, int argc) {
|
|
if (!args || argc < 3) {
|
|
return -1;
|
|
}
|
|
FILE *f = (FILE*)args[0];
|
|
int addr = (int)args[1];
|
|
int size = (int)args[2];
|
|
|
|
if (!f || addr < 0 || addr >= MEM_SIZE || size <= 0) {
|
|
return -1;
|
|
}
|
|
|
|
if (addr + size > MEM_SIZE) {
|
|
size = MEM_SIZE - addr;
|
|
}
|
|
|
|
char temp_buf[8192];
|
|
if (size > 8192) size = 8192;
|
|
|
|
int result = fread(temp_buf, 1, size, f);
|
|
if (result > 0) {
|
|
for (int i = 0; i < result && addr + i < MEM_SIZE; i++) {
|
|
memory[addr + i] = temp_buf[i];
|
|
}
|
|
}
|
|
return result;
|
|
}
|
|
|
|
long native_fwrite(long *args, int argc) {
|
|
if (!args || argc < 3) {
|
|
return -1;
|
|
}
|
|
FILE *f = (FILE*)args[0];
|
|
long buf_arg = args[1];
|
|
int size = (int)args[2];
|
|
|
|
if (!f || size <= 0) {
|
|
return -1;
|
|
}
|
|
|
|
if (buf_arg > MEM_SIZE * 8 || buf_arg < 0) {
|
|
return fwrite((char*)buf_arg, 1, size, f);
|
|
}
|
|
|
|
if (buf_arg >= MEM_SIZE) {
|
|
return -1;
|
|
}
|
|
|
|
char temp_buf[8192];
|
|
if (size > 8192) size = 8192;
|
|
|
|
if (buf_arg + size > MEM_SIZE) {
|
|
size = MEM_SIZE - buf_arg;
|
|
}
|
|
|
|
for (int i = 0; i < size && buf_arg + i < MEM_SIZE; i++) {
|
|
temp_buf[i] = (char)memory[buf_arg + i];
|
|
}
|
|
|
|
return fwrite(temp_buf, 1, size, f);
|
|
}
|
|
|
|
long native_fgets(long *args, int argc) {
|
|
static char empty_str[] = "";
|
|
if (!args || argc < 2) {
|
|
return (long)empty_str;
|
|
}
|
|
FILE *f = (FILE*)args[0];
|
|
int max_size = (int)args[1];
|
|
|
|
if (!f || max_size <= 0) {
|
|
return (long)empty_str;
|
|
}
|
|
|
|
if (str_pool_idx >= STR_POOL_SIZE) {
|
|
error("String pool overflow");
|
|
return (long)empty_str;
|
|
}
|
|
|
|
char *result = &str_pool[str_pool_idx];
|
|
if (max_size > STR_POOL_SIZE - str_pool_idx) {
|
|
max_size = STR_POOL_SIZE - str_pool_idx;
|
|
}
|
|
|
|
if (fgets(result, max_size, f) == NULL) {
|
|
return (long)empty_str;
|
|
}
|
|
|
|
int len = strlen(result);
|
|
str_pool_idx += len + 1;
|
|
return (long)result;
|
|
}
|
|
|
|
long native_fputs(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return -1;
|
|
}
|
|
FILE *f = (FILE*)args[0];
|
|
char *str = (char*)args[1];
|
|
|
|
if (!f || !str) {
|
|
return -1;
|
|
}
|
|
|
|
return fputs(str, f);
|
|
}
|
|
|
|
long native_feof(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return 1;
|
|
}
|
|
FILE *f = (FILE*)args[0];
|
|
if (!f) {
|
|
return 1;
|
|
}
|
|
return feof(f);
|
|
}
|
|
|
|
long native_ftell(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return -1;
|
|
}
|
|
FILE *f = (FILE*)args[0];
|
|
if (!f) {
|
|
return -1;
|
|
}
|
|
return ftell(f);
|
|
}
|
|
|
|
long native_fseek(long *args, int argc) {
|
|
if (!args || argc < 3) {
|
|
return -1;
|
|
}
|
|
FILE *f = (FILE*)args[0];
|
|
long offset = args[1];
|
|
int whence = (int)args[2];
|
|
|
|
if (!f) {
|
|
return -1;
|
|
}
|
|
return fseek(f, offset, whence);
|
|
}
|
|
|
|
long native_fremove(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return -1;
|
|
}
|
|
char *filename = (char*)args[0];
|
|
if (!filename) {
|
|
return -1;
|
|
}
|
|
return remove(filename);
|
|
}
|
|
|
|
long native_frename(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return -1;
|
|
}
|
|
char *oldname = (char*)args[0];
|
|
char *newname = (char*)args[1];
|
|
if (!oldname || !newname) {
|
|
return -1;
|
|
}
|
|
return rename(oldname, newname);
|
|
}
|
|
|
|
long native_SEEK_SET(long *args, int argc) {
|
|
return SEEK_SET;
|
|
}
|
|
|
|
long native_SEEK_CUR(long *args, int argc) {
|
|
return SEEK_CUR;
|
|
}
|
|
|
|
long native_SEEK_END(long *args, int argc) {
|
|
return SEEK_END;
|
|
}
|
|
|
|
long native_int_to_double(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return 0;
|
|
}
|
|
union { double d; long l; } u;
|
|
u.d = (double)args[0];
|
|
return u.l;
|
|
}
|
|
|
|
long native_double_to_int(long *args, int argc) {
|
|
if (!args || argc < 1) {
|
|
return 0;
|
|
}
|
|
union { double d; long l; } u;
|
|
u.l = args[0];
|
|
return (long)u.d;
|
|
}
|
|
|
|
long native_double_add(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return 0;
|
|
}
|
|
union { double d; long l; } u1, u2, result;
|
|
u1.l = args[0];
|
|
u2.l = args[1];
|
|
result.d = u1.d + u2.d;
|
|
return result.l;
|
|
}
|
|
|
|
long native_double_sub(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return 0;
|
|
}
|
|
union { double d; long l; } u1, u2, result;
|
|
u1.l = args[0];
|
|
u2.l = args[1];
|
|
result.d = u1.d - u2.d;
|
|
return result.l;
|
|
}
|
|
|
|
long native_double_mul(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return 0;
|
|
}
|
|
union { double d; long l; } u1, u2, result;
|
|
u1.l = args[0];
|
|
u2.l = args[1];
|
|
result.d = u1.d * u2.d;
|
|
return result.l;
|
|
}
|
|
|
|
long native_double_div(long *args, int argc) {
|
|
if (!args || argc < 2) {
|
|
return 0;
|
|
}
|
|
union { double d; long l; } u1, u2, result;
|
|
u1.l = args[0];
|
|
u2.l = args[1];
|
|
if (u2.d != 0.0) {
|
|
result.d = u1.d / u2.d;
|
|
} else {
|
|
result.d = 0.0;
|
|
}
|
|
return result.l;
|
|
}
|
|
|
|
void register_native_functions() {
|
|
register_native_func("socket", native_socket);
|
|
register_native_func("bind", native_bind);
|
|
register_native_func("listen", native_listen);
|
|
register_native_func("accept", native_accept);
|
|
register_native_func("recv", native_recv);
|
|
register_native_func("send", native_send);
|
|
register_native_func("close", native_close);
|
|
register_native_func("strlen", native_strlen);
|
|
register_native_func("AF_INET", native_AF_INET);
|
|
register_native_func("SOCK_STREAM", native_SOCK_STREAM);
|
|
register_native_func("sqrt", native_sqrt);
|
|
register_native_func("pow", native_pow);
|
|
register_native_func("sin", native_sin);
|
|
register_native_func("cos", native_cos);
|
|
register_native_func("tan", native_tan);
|
|
register_native_func("abs", native_abs);
|
|
register_native_func("floor", native_floor);
|
|
register_native_func("ceil", native_ceil);
|
|
register_native_func("strpos", native_strpos);
|
|
register_native_func("substr", native_substr);
|
|
register_native_func("upper", native_upper);
|
|
register_native_func("lower", native_lower);
|
|
register_native_func("strip", native_strip);
|
|
register_native_func("replace", native_replace);
|
|
register_native_func("startswith", native_startswith);
|
|
register_native_func("endswith", native_endswith);
|
|
register_native_func("fopen", native_fopen);
|
|
register_native_func("fclose", native_fclose);
|
|
register_native_func("fread", native_fread);
|
|
register_native_func("fwrite", native_fwrite);
|
|
register_native_func("fgets", native_fgets);
|
|
register_native_func("fputs", native_fputs);
|
|
register_native_func("feof", native_feof);
|
|
register_native_func("ftell", native_ftell);
|
|
register_native_func("fseek", native_fseek);
|
|
register_native_func("fremove", native_fremove);
|
|
register_native_func("frename", native_frename);
|
|
register_native_func("SEEK_SET", native_SEEK_SET);
|
|
register_native_func("SEEK_CUR", native_SEEK_CUR);
|
|
register_native_func("SEEK_END", native_SEEK_END);
|
|
register_native_func("int_to_double", native_int_to_double);
|
|
register_native_func("double_to_int", native_double_to_int);
|
|
register_native_func("double_add", native_double_add);
|
|
register_native_func("double_sub", native_double_sub);
|
|
register_native_func("double_mul", native_double_mul);
|
|
register_native_func("double_div", native_double_div);
|
|
}
|