mirror of
https://github.com/kanjitalk755/macemu.git
synced 2024-11-23 04:33:24 +00:00
Added tap support to etherslave tool.
This commit is contained in:
parent
c939be2d2d
commit
19b53082a3
@ -43,15 +43,27 @@
|
|||||||
|
|
||||||
#include <Carbon/Carbon.h>
|
#include <Carbon/Carbon.h>
|
||||||
|
|
||||||
|
#define STR_MAX 256
|
||||||
|
#define MAX_ARGV 10
|
||||||
|
|
||||||
static int open_bpf(char *ifname);
|
static int open_bpf(char *ifname);
|
||||||
|
static int open_tap(char *ifname);
|
||||||
static int retreive_auth_info(void);
|
static int retreive_auth_info(void);
|
||||||
static int main_loop(int sd);
|
static int main_loop(int sd, int use_bpf);
|
||||||
|
static int run_cmd(const char *cmd);
|
||||||
|
static void handler(int signum);
|
||||||
|
static int install_signal_handlers();
|
||||||
|
static void do_exit();
|
||||||
|
|
||||||
|
static int removeBridge = 0;
|
||||||
|
|
||||||
int main(int argc, char **argv)
|
int main(int argc, char **argv)
|
||||||
{
|
{
|
||||||
char *if_name;
|
char *if_name;
|
||||||
int ret;
|
int ret = 255;
|
||||||
int sd;
|
int sd;
|
||||||
|
int tapNum;
|
||||||
|
int use_bpf;
|
||||||
|
|
||||||
if (argc != 2) {
|
if (argc != 2) {
|
||||||
return 255;
|
return 255;
|
||||||
@ -59,32 +71,41 @@ int main(int argc, char **argv)
|
|||||||
|
|
||||||
if_name = argv[1];
|
if_name = argv[1];
|
||||||
|
|
||||||
|
do {
|
||||||
ret = retreive_auth_info();
|
ret = retreive_auth_info();
|
||||||
if (ret != 0) {
|
if (ret != 0) {
|
||||||
return 254;
|
ret = 254;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
fflush(stdout);
|
if(sscanf(if_name, "tap%d", &tapNum) == 1) {
|
||||||
|
sd = open_tap(if_name);
|
||||||
|
use_bpf = 0;
|
||||||
|
} else {
|
||||||
sd = open_bpf(if_name);
|
sd = open_bpf(if_name);
|
||||||
|
use_bpf = 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (sd < 0) {
|
if (sd < 0) {
|
||||||
return 253;
|
ret = 253;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
fflush(stdout);
|
if(install_signal_handlers() != 0) {
|
||||||
|
ret = 252;
|
||||||
ret = main_loop(sd);
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = main_loop(sd, use_bpf);
|
||||||
close(sd);
|
close(sd);
|
||||||
|
} while(0);
|
||||||
|
|
||||||
if (ret < 0) {
|
do_exit();
|
||||||
return 252;
|
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
static int main_loop(int sd, int use_bpf)
|
||||||
}
|
|
||||||
|
|
||||||
static int main_loop(int sd)
|
|
||||||
{
|
{
|
||||||
fd_set readSet;
|
fd_set readSet;
|
||||||
char *outgoing, *incoming;
|
char *outgoing, *incoming;
|
||||||
@ -98,10 +119,15 @@ static int main_loop(int sd)
|
|||||||
int pkt_len;
|
int pkt_len;
|
||||||
int frame_len;
|
int frame_len;
|
||||||
int pad;
|
int pad;
|
||||||
|
char c = 0;
|
||||||
|
|
||||||
|
if(use_bpf) {
|
||||||
if (ioctl(sd, BIOCGBLEN, &blen) < 0) {
|
if (ioctl(sd, BIOCGBLEN, &blen) < 0) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
blen = 2048;
|
||||||
|
}
|
||||||
|
|
||||||
incoming = malloc(blen);
|
incoming = malloc(blen);
|
||||||
if (incoming == NULL) {
|
if (incoming == NULL) {
|
||||||
@ -119,6 +145,9 @@ static int main_loop(int sd)
|
|||||||
|
|
||||||
out_len = (unsigned short *)outgoing;
|
out_len = (unsigned short *)outgoing;
|
||||||
|
|
||||||
|
/* Let our parent know we are ready for business. */
|
||||||
|
write(0, &c, 1);
|
||||||
|
|
||||||
while (1) {
|
while (1) {
|
||||||
int i;
|
int i;
|
||||||
FD_ZERO(&readSet);
|
FD_ZERO(&readSet);
|
||||||
@ -164,7 +193,7 @@ static int main_loop(int sd)
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (FD_ISSET(sd, &readSet)) {
|
if (use_bpf && FD_ISSET(sd, &readSet)) {
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
ret = read(sd, incoming, blen);
|
ret = read(sd, incoming, blen);
|
||||||
@ -186,7 +215,11 @@ static int main_loop(int sd)
|
|||||||
}
|
}
|
||||||
*in_len = pkt_len;
|
*in_len = pkt_len;
|
||||||
|
|
||||||
write(0, in_len, pkt_len + 2);
|
if(write(0, in_len, pkt_len + 2) < (pkt_len + 2)) {
|
||||||
|
fret = -10;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
if ((frame_len & 0x03) == 0) {
|
if ((frame_len & 0x03) == 0) {
|
||||||
pad = 0;
|
pad = 0;
|
||||||
} else {
|
} else {
|
||||||
@ -202,6 +235,24 @@ static int main_loop(int sd)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!use_bpf && FD_ISSET(sd, &readSet)) {
|
||||||
|
in_len = (unsigned short *)incoming;
|
||||||
|
|
||||||
|
pkt_len = read(sd, incoming+2, blen-2);
|
||||||
|
if (pkt_len < 14) {
|
||||||
|
fret = -8;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
*in_len = ret;
|
||||||
|
if(write(0, in_len, pkt_len + 2) < (pkt_len + 2)) {
|
||||||
|
fret = -10;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
free(incoming);
|
free(incoming);
|
||||||
@ -256,6 +307,44 @@ static int retreive_auth_info(void)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int open_tap(char *ifname)
|
||||||
|
{
|
||||||
|
char str[STR_MAX] = {0};
|
||||||
|
int sd;
|
||||||
|
|
||||||
|
snprintf(str, STR_MAX, "/dev/%s", ifname);
|
||||||
|
|
||||||
|
sd = open(str, O_RDWR);
|
||||||
|
if(sd < 0) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
snprintf(str, STR_MAX, "/sbin/ifconfig %s up", ifname);
|
||||||
|
if(run_cmd(str) != 0) {
|
||||||
|
close(sd);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
snprintf(str, STR_MAX, "/sbin/ifconfig bridge0 create");
|
||||||
|
if(run_cmd(str) == 0) {
|
||||||
|
removeBridge = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
snprintf(str, STR_MAX, "/sbin/ifconfig bridge0 addm %s", ifname);
|
||||||
|
if(run_cmd(str) != 0) {
|
||||||
|
close(sd);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
snprintf(str, STR_MAX, "/sbin/ifconfig bridge0 up");
|
||||||
|
if(run_cmd(str) != 0) {
|
||||||
|
close(sd);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return sd;
|
||||||
|
}
|
||||||
|
|
||||||
static int open_bpf(char *ifname)
|
static int open_bpf(char *ifname)
|
||||||
{
|
{
|
||||||
u_int blen = 0;
|
u_int blen = 0;
|
||||||
@ -302,3 +391,83 @@ static int open_bpf(char *ifname)
|
|||||||
|
|
||||||
return sd;
|
return sd;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int run_cmd(const char *cmd) {
|
||||||
|
char cmd_buffer[STR_MAX] = {0};
|
||||||
|
char *argv[MAX_ARGV + 1] = {0};
|
||||||
|
int i;
|
||||||
|
pid_t pid, waitpid;
|
||||||
|
int status = 0;
|
||||||
|
|
||||||
|
/* Collect arguments */
|
||||||
|
strncpy(cmd_buffer, cmd, STR_MAX-1);
|
||||||
|
|
||||||
|
argv[0] = strtok(cmd_buffer, " ");
|
||||||
|
for (i=1; i<MAX_ARGV; ++i) {
|
||||||
|
argv[i] = strtok(NULL, " ");
|
||||||
|
if (argv[i] == NULL) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Run sub process */
|
||||||
|
pid = fork();
|
||||||
|
if (pid == 0) {
|
||||||
|
|
||||||
|
/* Child process */
|
||||||
|
fclose(stdout);
|
||||||
|
fclose(stderr);
|
||||||
|
|
||||||
|
if (execve(argv[0], argv, NULL) < 0) {
|
||||||
|
perror("execve");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
/* Wait for child to exit */
|
||||||
|
waitpid = wait(&status);
|
||||||
|
if (waitpid < 0) {
|
||||||
|
perror("wait");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (status != 0) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void handler(int signum) {
|
||||||
|
do_exit();
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int install_signal_handlers() {
|
||||||
|
struct sigaction act = {0};
|
||||||
|
|
||||||
|
act.sa_handler = handler;
|
||||||
|
sigemptyset(&act.sa_mask);
|
||||||
|
|
||||||
|
if(sigaction(SIGINT, &act, NULL) != 0) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
if(sigaction(SIGHUP, &act, NULL) != 0) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
if(sigaction(SIGTERM, &act, NULL) != 0) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void do_exit() {
|
||||||
|
if(removeBridge) {
|
||||||
|
run_cmd("/sbin/ifconfig bridge0 destroy");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -57,6 +57,7 @@ FILE * run_tool(const char *if_name, const char *tool_name)
|
|||||||
CFURLRef url_ref;
|
CFURLRef url_ref;
|
||||||
CFStringRef path_str;
|
CFStringRef path_str;
|
||||||
CFStringRef tool_name_str;
|
CFStringRef tool_name_str;
|
||||||
|
char c;
|
||||||
|
|
||||||
bundle_ref = CFBundleGetMainBundle();
|
bundle_ref = CFBundleGetMainBundle();
|
||||||
if(bundle_ref == NULL) {
|
if(bundle_ref == NULL) {
|
||||||
@ -68,6 +69,7 @@ FILE * run_tool(const char *if_name, const char *tool_name)
|
|||||||
|
|
||||||
url_ref = CFBundleCopyResourceURL(bundle_ref, tool_name_str,
|
url_ref = CFBundleCopyResourceURL(bundle_ref, tool_name_str,
|
||||||
NULL, NULL);
|
NULL, NULL);
|
||||||
|
CFRelease(tool_name_str);
|
||||||
|
|
||||||
if(url_ref == NULL) {
|
if(url_ref == NULL) {
|
||||||
return NULL;
|
return NULL;
|
||||||
@ -80,7 +82,6 @@ FILE * run_tool(const char *if_name, const char *tool_name)
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
CFIndex index = CFStringGetLength(path_str);
|
|
||||||
if(!CFStringGetCString(path_str, path_buffer, sizeof(path_buffer),
|
if(!CFStringGetCString(path_str, path_buffer, sizeof(path_buffer),
|
||||||
kCFStringEncodingUTF8)) {
|
kCFStringEncodingUTF8)) {
|
||||||
CFRelease(path_str);
|
CFRelease(path_str);
|
||||||
@ -126,5 +127,10 @@ FILE * run_tool(const char *if_name, const char *tool_name)
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(fread(&c, 1, 1, fp) != 1) {
|
||||||
|
fclose(fp);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
return fp;
|
return fp;
|
||||||
}
|
}
|
||||||
|
@ -1161,16 +1161,16 @@ static bool open_ether_slave(const char *if_name)
|
|||||||
FILE *fp;
|
FILE *fp;
|
||||||
char str[64];
|
char str[64];
|
||||||
|
|
||||||
if (get_mac_address(if_name, ether_addr) != 0) {
|
fp = run_tool(if_name, "etherslavetool");
|
||||||
snprintf(str, sizeof(str), "Unable to find interface %s.",
|
if (fp == NULL) {
|
||||||
if_name);
|
snprintf(str, sizeof(str), "Unable to run ether slave helper tool.");
|
||||||
WarningAlert(str);
|
WarningAlert(str);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
fp = run_tool(if_name, "etherslavetool");
|
if (get_mac_address(if_name, ether_addr) != 0) {
|
||||||
if (fp == NULL) {
|
snprintf(str, sizeof(str), "Unable to find interface %s.",
|
||||||
snprintf(str, sizeof(str), "Unable to run ether slave helper tool.");
|
if_name);
|
||||||
WarningAlert(str);
|
WarningAlert(str);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user