优化同一设备的互斥锁处理

This commit is contained in:
gb 2022-05-16 17:26:36 +08:00
parent 46023bbb53
commit be9e3ad347
3 changed files with 77 additions and 7 deletions

View File

@ -156,20 +156,50 @@ void shared_memory::init(void)
int obj = shmget(key_, bytes_, IPC_EXCL | IPC_CREAT | 0600);
if (obj < 0)
{
unsigned int* v = (unsigned int*)&key_;
if (errno == EEXIST)
{
first_ = false;
obj = shmget(key_, bytes_, 0600);
if(read().empty())
if(obj == -1)
obj = shmget(key_, bytes_, 0);
HG_VLOG_MINI_3(HG_LOG_LEVEL_DEBUG_INFO, "open existing: shmget(0x%x%08x) = %d\n", v[1], v[0], obj);
obj_ = (void*)obj;
std::string prev(read()), proc("");
HG_VLOG_MINI_1(HG_LOG_LEVEL_DEBUG_INFO, "shared memory content: %s\n", prev.c_str());
if(prev.length())
{
proc = prev;
size_t pos = proc.find("pid: ");
if (pos != std::string::npos)
proc.erase(0, pos + 5);
pos = proc.find(")");
if (pos != std::string::npos)
proc.erase(pos);
proc = shared_memory::get_proc_name_by_pid(atoi(proc.c_str()));
if (proc.length())
{
pos = prev.find("(");
if (pos == std::string::npos)
pos = prev.length();
if (strcasecmp(proc.c_str(), prev.substr(0, pos).c_str()))
proc = "";
}
}
if (proc.empty())
{
first_ = true;
clear();
obj = shmget(key_, bytes_, IPC_EXCL | IPC_CREAT | 0600);
HG_VLOG_MINI_1(HG_LOG_LEVEL_DEBUG_INFO, "shared memory id(%d) already exists but is not accessible, close and reopen it\n", obj);
HG_VLOG_MINI_1(HG_LOG_LEVEL_DEBUG_INFO, "%s is not existing and reopen it\n", prev.c_str());
}
}
else
{
HG_VLOG_MINI_3(HG_LOG_LEVEL_DEBUG_INFO, "shmget(0x%x%08x) = %d\n", v[1], v[0], errno);
return;
}
}
obj_ = (void*)obj;
HG_VLOG_MINI_2(HG_LOG_LEVEL_DEBUG_INFO, "shared memory id = %d[%s], \n", obj, first_ ? "created" : "opened");
@ -232,6 +262,42 @@ void shared_memory::release_buf(void* buf)
#endif
}
#ifndef WIN32
std::string shared_memory::get_proc_name_by_pid(pid_t pid)
{
char path[512] = { 0 };
unsigned int* v = (unsigned int*)&pid;
std::string ret("");
if (sizeof(pid) > 4 && v[1])
sprintf(path, "/proc/%lld/status", pid);
else
sprintf(path, "/proc/%u/status", pid);
FILE* src = fopen(path, "rb");
if (src)
{
char val[512] = { 0 };
memset(path, 0, sizeof(path));
fgets(path, sizeof(path) - 1, src);
fclose(src);
sscanf(path, "%*s %s", val);
ret = val;
}
if (sizeof(pid) > 4 && v[1])
{
HG_VLOG_MINI_2(HG_LOG_LEVEL_DEBUG_INFO, "PID(%lld) name is: %s\n", pid, ret.c_str());
}
else
{
HG_VLOG_MINI_2(HG_LOG_LEVEL_DEBUG_INFO, "PID(%u) name is: %s\n", pid, ret.c_str());
}
return ret;
}
#endif
bool shared_memory::is_ok(void)
{
return obj_ != nullptr;

View File

@ -110,6 +110,10 @@ class shared_memory : public refer
char* get_buf(void);
void release_buf(void* buf);
#ifndef WIN32
static std::string get_proc_name_by_pid(pid_t pid);
#endif
public:
shared_memory(unsigned long long key, size_t size = 1024);

View File

@ -497,7 +497,7 @@ void usb_manager::enum_endpoints(libusb_device* device, USBTRANSENDP* endp)
else
s = &ep->out; // = (conf->interface[j].altsetting[k].endpoint[l].bEndpointAddress & 3) | LIBUSB_ENDPOINT_OUT;
// NOTE: 这里应该尽量将输入输出端口统一到同一个接口上来,目前未做,只取第一个
// NOTE: 这里应该尽é‡<EFBFBD>将输入输出端å<EFBFBD>£ç»Ÿä¸€åˆ°å<EFBFBD>Œä¸€ä¸ªæŽ¥å<EFBFBD>£ä¸Šæ<EFBFBD>¥ï¼Œç®å‰<EFBFBD>未å<EFBFBD>šï¼Œå<EFBFBD>ªå<EFBFBD>第一ä¸?
if (s->port == usb_manager::uninit_uint8)
{
s->port = conf->interface[j].altsetting[k].endpoint[l].bEndpointAddress & (LIBUSB_ENDPOINT_IN | LIBUSB_ENDPOINT_OUT | 3);
@ -626,14 +626,14 @@ bool usb_io::make_singleton(void)
return true;
}
char msg[128] = { 0 };
std::string str(singleton_->read());
singleton_->release();
singleton_ = nullptr;
last_err_ = HG_ERR_OPENED_BY_OTHER_PROCESS;
sprintf(msg, "\350\256\276\345\244\207\345\267\262\347\273\217\350\242\253\350\277\233\347\250\213%s\345\215\240\347\224\250", str.c_str());
init_err_msg_ = msg;
str.insert(0, "\350\256\276\345\244\207\345\267\262\347\273\217\350\242\253\350\277\233\347\250\213 '");
str += "' \345\215\240\347\224\250";
init_err_msg_ = str;
return false;
}
@ -791,7 +791,7 @@ bool usb_io::on_io_error(hg_err err, usb_manager::USBSIMPLEX* endp)
if (err == HG_ERR_TIMEOUT)
{
//因为在发送img参数出现timeout暂时禁用
//å ä¸ºåœ¨å<EFBFBD>é€<EFBFBD>imgå<EFBFBD>数出现timeout,æšæ—¶ç¦<EFBFBD>ç”?
// //HG_LOG(HG_LOG_LEVEL_DEBUG_INFO, "Operation timeout\n");
// libusb_clear_halt(handle_, endp->port);