diff --git a/src/cardreader.cpp b/src/cardreader.cpp index e858808..4ab9e45 100644 --- a/src/cardreader.cpp +++ b/src/cardreader.cpp @@ -333,6 +333,24 @@ void CardReader::HandleReaderStatusChange(uv_async_t *handle, int status) { AsyncResult* ar = async_baton->async_result; + if ((ar->result == SCARD_S_SUCCESS) || (ar->result == (LONG)SCARD_E_NO_READERS_AVAILABLE)) { + const unsigned argc = 3; + Local argv[argc] = { + Nan::Undefined(), // argument + Nan::New(ar->status), + Nan::CopyBuffer(reinterpret_cast(ar->atr), ar->atrlen).ToLocalChecked() + }; + + Nan::Callback(Nan::New(async_baton->callback)).Call(argc, argv); + } else { + Local err = Nan::Error(error_msg("SCardGetStatusChange", ar->result).c_str()); + // Prepare the parameters for the callback function. + const unsigned argc = 1; + Local argv[argc] = { err }; + Nan::Callback(Nan::New(async_baton->callback)).Call(argc, argv); + } + + // Do exit, after throwing last events if (ar->do_exit) { uv_close(reinterpret_cast(&async_baton->async), CloseCallback); // necessary otherwise UV will block @@ -342,23 +360,6 @@ void CardReader::HandleReaderStatusChange(uv_async_t *handle, int status) { }; Nan::MakeCallback(async_baton->reader->handle(), "emit", 1, argv); - } else { - if (ar->result == SCARD_S_SUCCESS) { - const unsigned argc = 3; - Local argv[argc] = { - Nan::Undefined(), // argument - Nan::New(ar->status), - Nan::CopyBuffer(reinterpret_cast(ar->atr), ar->atrlen).ToLocalChecked() - }; - - Nan::Callback(Nan::New(async_baton->callback)).Call(argc, argv); - } else { - Local err = Nan::Error(error_msg("SCardGetStatusChange", ar->result).c_str()); - // Prepare the parameters for the callback function. - const unsigned argc = 1; - Local argv[argc] = { err }; - Nan::Callback(Nan::New(async_baton->callback)).Call(argc, argv); - } } if (reader->m_status_thread) { @@ -392,20 +393,21 @@ void CardReader::HandlerFunction(void* arg) { if (!keep_watching) { reader->m_state = 2; + async_baton->async_result->do_exit = true; } - uv_mutex_unlock(&reader->m_mutex); - async_baton->async_result->result = result; async_baton->async_result->status = card_reader_state.dwEventState; memcpy(async_baton->async_result->atr, card_reader_state.rgbAtr, card_reader_state.cbAtr); async_baton->async_result->atrlen = card_reader_state.cbAtr; + + uv_mutex_unlock(&reader->m_mutex); + uv_async_send(&async_baton->async); card_reader_state.dwCurrentState = card_reader_state.dwEventState; } - async_baton->async_result->do_exit = true; - uv_async_send(&async_baton->async); + // Exit flag set in keepwatching and handled in following uv_async_send } void CardReader::DoConnect(uv_work_t* req) { diff --git a/src/pcsclite.cpp b/src/pcsclite.cpp index a53b850..bb91915 100644 --- a/src/pcsclite.cpp +++ b/src/pcsclite.cpp @@ -124,11 +124,6 @@ void PCSCLite::HandleReaderStatusChange(uv_async_t *handle, int status) { AsyncBaton* async_baton = static_cast(handle->data); AsyncResult* ar = async_baton->async_result; - if (ar->do_exit) { - uv_close(reinterpret_cast(&async_baton->async), CloseCallback); // necessary otherwise UV will block - return; - } - if ((ar->result == SCARD_S_SUCCESS) || (ar->result == (LONG)SCARD_E_NO_READERS_AVAILABLE)) { const unsigned argc = 2; Local argv[argc] = { @@ -145,6 +140,12 @@ void PCSCLite::HandleReaderStatusChange(uv_async_t *handle, int status) { Nan::Callback(Nan::New(async_baton->callback)).Call(argc, argv); } + // Do exit, after throwing last events + if (ar->do_exit) { + uv_close(reinterpret_cast(&async_baton->async), CloseCallback); // necessary otherwise UV will block + return; + } + /* reset AsyncResult */ delete [] ar->readers_name; ar->readers_name = NULL;