|
|
@ -1046,7 +1046,6 @@ void usb_applog(struct cgpu_info *cgpu, enum usb_cmds cmd, char *msg, int amount |
|
|
|
err, amount); |
|
|
|
err, amount); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
#ifdef WIN32 |
|
|
|
|
|
|
|
static void in_use_store_ress(uint8_t bus_number, uint8_t device_address, void *resource1, void *resource2) |
|
|
|
static void in_use_store_ress(uint8_t bus_number, uint8_t device_address, void *resource1, void *resource2) |
|
|
|
{ |
|
|
|
{ |
|
|
|
struct usb_in_use_list *in_use_tmp; |
|
|
|
struct usb_in_use_list *in_use_tmp; |
|
|
@ -1118,7 +1117,6 @@ static void in_use_get_ress(uint8_t bus_number, uint8_t device_address, void **r |
|
|
|
applog(LOG_ERR, "FAIL: USB get_lock empty (%d:%d)", |
|
|
|
applog(LOG_ERR, "FAIL: USB get_lock empty (%d:%d)", |
|
|
|
(int)bus_number, (int)device_address); |
|
|
|
(int)bus_number, (int)device_address); |
|
|
|
} |
|
|
|
} |
|
|
|
#endif |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
static bool __is_in_use(uint8_t bus_number, uint8_t device_address) |
|
|
|
static bool __is_in_use(uint8_t bus_number, uint8_t device_address) |
|
|
|
{ |
|
|
|
{ |
|
|
@ -3176,8 +3174,9 @@ fail: |
|
|
|
struct semid_ds seminfo; |
|
|
|
struct semid_ds seminfo; |
|
|
|
union semun opt; |
|
|
|
union semun opt; |
|
|
|
char name[64]; |
|
|
|
char name[64]; |
|
|
|
key_t key; |
|
|
|
key_t *key; |
|
|
|
int fd, sem, count; |
|
|
|
int *sem; |
|
|
|
|
|
|
|
int fd, count; |
|
|
|
|
|
|
|
|
|
|
|
if (is_in_use_bd(bus_number, device_address)) |
|
|
|
if (is_in_use_bd(bus_number, device_address)) |
|
|
|
return false; |
|
|
|
return false; |
|
|
@ -3188,25 +3187,34 @@ fail: |
|
|
|
applog(LOG_ERR, |
|
|
|
applog(LOG_ERR, |
|
|
|
"SEM: %s USB open failed '%s' err (%d) %s", |
|
|
|
"SEM: %s USB open failed '%s' err (%d) %s", |
|
|
|
dname, name, errno, strerror(errno)); |
|
|
|
dname, name, errno, strerror(errno)); |
|
|
|
return false; |
|
|
|
goto _out; |
|
|
|
} |
|
|
|
} |
|
|
|
close(fd); |
|
|
|
close(fd); |
|
|
|
key = ftok(name, 'K'); |
|
|
|
|
|
|
|
sem = semget(key, 1, IPC_CREAT | IPC_EXCL | 438); |
|
|
|
key = malloc(sizeof(*key)); |
|
|
|
if (sem < 0) { |
|
|
|
if (unlikely(!key)) |
|
|
|
|
|
|
|
quit(1, "SEM: Failed to malloc key"); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
sem = malloc(sizeof(*sem)); |
|
|
|
|
|
|
|
if (unlikely(!sem)) |
|
|
|
|
|
|
|
quit(1, "SEM: Failed to malloc sem"); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
*key = ftok(name, 'K'); |
|
|
|
|
|
|
|
*sem = semget(*key, 1, IPC_CREAT | IPC_EXCL | 438); |
|
|
|
|
|
|
|
if (*sem < 0) { |
|
|
|
if (errno != EEXIST) { |
|
|
|
if (errno != EEXIST) { |
|
|
|
applog(LOG_ERR, |
|
|
|
applog(LOG_ERR, |
|
|
|
"SEM: %s USB failed to get '%s' err (%d) %s", |
|
|
|
"SEM: %s USB failed to get '%s' err (%d) %s", |
|
|
|
dname, name, errno, strerror(errno)); |
|
|
|
dname, name, errno, strerror(errno)); |
|
|
|
return false; |
|
|
|
goto free_out; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
sem = semget(key, 1, 0); |
|
|
|
*sem = semget(*key, 1, 0); |
|
|
|
if (sem < 0) { |
|
|
|
if (*sem < 0) { |
|
|
|
applog(LOG_ERR, |
|
|
|
applog(LOG_ERR, |
|
|
|
"SEM: %s USB failed to access '%s' err (%d) %s", |
|
|
|
"SEM: %s USB failed to access '%s' err (%d) %s", |
|
|
|
dname, name, errno, strerror(errno)); |
|
|
|
dname, name, errno, strerror(errno)); |
|
|
|
return false; |
|
|
|
goto free_out; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
opt.buf = &seminfo; |
|
|
|
opt.buf = &seminfo; |
|
|
@ -3216,14 +3224,14 @@ fail: |
|
|
|
if (count > 99) { |
|
|
|
if (count > 99) { |
|
|
|
applog(LOG_ERR, |
|
|
|
applog(LOG_ERR, |
|
|
|
"SEM: %s USB timeout waiting for (%d) '%s'", |
|
|
|
"SEM: %s USB timeout waiting for (%d) '%s'", |
|
|
|
dname, sem, name); |
|
|
|
dname, *sem, name); |
|
|
|
return false; |
|
|
|
goto free_out; |
|
|
|
} |
|
|
|
} |
|
|
|
if (semctl(sem, 0, IPC_STAT, opt) == -1) { |
|
|
|
if (semctl(*sem, 0, IPC_STAT, opt) == -1) { |
|
|
|
applog(LOG_ERR, |
|
|
|
applog(LOG_ERR, |
|
|
|
"SEM: %s USB failed to wait for (%d) '%s' count %d err (%d) %s", |
|
|
|
"SEM: %s USB failed to wait for (%d) '%s' count %d err (%d) %s", |
|
|
|
dname, sem, name, count, errno, strerror(errno)); |
|
|
|
dname, *sem, name, count, errno, strerror(errno)); |
|
|
|
return false; |
|
|
|
goto free_out; |
|
|
|
} |
|
|
|
} |
|
|
|
if (opt.buf->sem_otime != 0) |
|
|
|
if (opt.buf->sem_otime != 0) |
|
|
|
break; |
|
|
|
break; |
|
|
@ -3236,22 +3244,29 @@ fail: |
|
|
|
{ 0, 1, IPC_NOWAIT | SEM_UNDO } |
|
|
|
{ 0, 1, IPC_NOWAIT | SEM_UNDO } |
|
|
|
}; |
|
|
|
}; |
|
|
|
|
|
|
|
|
|
|
|
if (semop(sem, sops, 2)) { |
|
|
|
if (semop(*sem, sops, 2)) { |
|
|
|
if (errno == EAGAIN) { |
|
|
|
if (errno == EAGAIN) { |
|
|
|
if (!hotplug_mode) |
|
|
|
if (!hotplug_mode) |
|
|
|
applog(LOG_WARNING, |
|
|
|
applog(LOG_WARNING, |
|
|
|
"SEM: %s USB failed to get (%d) '%s' - device in use", |
|
|
|
"SEM: %s USB failed to get (%d) '%s' - device in use", |
|
|
|
dname, sem, name); |
|
|
|
dname, *sem, name); |
|
|
|
} else { |
|
|
|
} else { |
|
|
|
applog(LOG_DEBUG, |
|
|
|
applog(LOG_DEBUG, |
|
|
|
"SEM: %s USB failed to get (%d) '%s' err (%d) %s", |
|
|
|
"SEM: %s USB failed to get (%d) '%s' err (%d) %s", |
|
|
|
dname, sem, name, errno, strerror(errno)); |
|
|
|
dname, *sem, name, errno, strerror(errno)); |
|
|
|
} |
|
|
|
} |
|
|
|
return false; |
|
|
|
goto free_out; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
add_in_use(bus_number, device_address); |
|
|
|
add_in_use(bus_number, device_address); |
|
|
|
|
|
|
|
in_use_store_ress(bus_number, device_address, (void *)key, (void *)sem); |
|
|
|
return true; |
|
|
|
return true; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
free_out: |
|
|
|
|
|
|
|
free(sem); |
|
|
|
|
|
|
|
free(key); |
|
|
|
|
|
|
|
_out: |
|
|
|
|
|
|
|
return false; |
|
|
|
#endif |
|
|
|
#endif |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
@ -3288,27 +3303,15 @@ fila: |
|
|
|
return; |
|
|
|
return; |
|
|
|
#else |
|
|
|
#else |
|
|
|
char name[64]; |
|
|
|
char name[64]; |
|
|
|
key_t key; |
|
|
|
key_t *key = NULL; |
|
|
|
int fd, sem; |
|
|
|
int *sem = NULL; |
|
|
|
|
|
|
|
|
|
|
|
sprintf(name, "/tmp/cgminer-usb-%d-%d", (int)bus_number, (int)device_address); |
|
|
|
sprintf(name, "/tmp/cgminer-usb-%d-%d", (int)bus_number, (int)device_address); |
|
|
|
fd = open(name, O_CREAT|O_RDONLY, S_IRUSR|S_IWUSR|S_IRGRP|S_IROTH); |
|
|
|
|
|
|
|
if (fd == -1) { |
|
|
|
|
|
|
|
applog(LOG_ERR, |
|
|
|
|
|
|
|
"SEM: %s USB open failed '%s' for release err (%d) %s", |
|
|
|
|
|
|
|
dname, name, errno, strerror(errno)); |
|
|
|
|
|
|
|
return; |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
close(fd); |
|
|
|
|
|
|
|
key = ftok(name, 'K'); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
sem = semget(key, 1, 0); |
|
|
|
in_use_get_ress(bus_number, device_address, (void **)(&key), (void **)(&sem)); |
|
|
|
if (sem < 0) { |
|
|
|
|
|
|
|
applog(LOG_ERR, |
|
|
|
if (!key || !sem) |
|
|
|
"SEM: %s USB failed to get '%s' for release err (%d) %s", |
|
|
|
goto fila; |
|
|
|
dname, name, errno, strerror(errno)); |
|
|
|
|
|
|
|
return; |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
struct sembuf sops[] = { |
|
|
|
struct sembuf sops[] = { |
|
|
|
{ 0, -1, SEM_UNDO } |
|
|
|
{ 0, -1, SEM_UNDO } |
|
|
@ -3318,12 +3321,22 @@ fila: |
|
|
|
// exceeding this timeout means it would probably never succeed anyway
|
|
|
|
// exceeding this timeout means it would probably never succeed anyway
|
|
|
|
struct timespec timeout = { 0, 10000000 }; |
|
|
|
struct timespec timeout = { 0, 10000000 }; |
|
|
|
|
|
|
|
|
|
|
|
if (semtimedop(sem, sops, 1, &timeout)) { |
|
|
|
if (semtimedop(*sem, sops, 1, &timeout)) { |
|
|
|
applog(LOG_ERR, |
|
|
|
applog(LOG_ERR, |
|
|
|
"SEM: %s USB failed to release '%s' err (%d) %s", |
|
|
|
"SEM: %s USB failed to release '%s' err (%d) %s", |
|
|
|
dname, name, errno, strerror(errno)); |
|
|
|
dname, name, errno, strerror(errno)); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (semctl(*sem, 0, IPC_RMID)) { |
|
|
|
|
|
|
|
applog(LOG_WARNING, |
|
|
|
|
|
|
|
"SEM: %s USB failed to remove SEM '%s' err (%d) %s", |
|
|
|
|
|
|
|
dname, name, errno, strerror(errno)); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
fila: |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
free(sem); |
|
|
|
|
|
|
|
free(key); |
|
|
|
remove_in_use(bus_number, device_address); |
|
|
|
remove_in_use(bus_number, device_address); |
|
|
|
return; |
|
|
|
return; |
|
|
|
#endif |
|
|
|
#endif |
|
|
|