/// \brief Releases an aquired lock on the mutex
    void unlock()
    {
        WINSTL_ASSERT(NULL != m_mx);

        if(!::ReleaseMutex(m_mx))
        {
            DWORD const e = ::GetLastError();

#ifdef STLSOFT_CF_EXCEPTION_SUPPORT
# if STLSOFT_LEAD_VER >= 0x010a0000
            STLSOFT_THROW_X(synchronisation_object_state_change_failed_exception(e, "mutex release failed", Synchronisation_MutexReleaseFailed));
# else /* ? STLSOFT_LEAD_VER >= 1.10 */
            STLSOFT_THROW_X(synchronisation_exception("mutex release failed", e));
# endif /* STLSOFT_LEAD_VER >= 1.10 */
#endif /* STLSOFT_CF_EXCEPTION_SUPPORT */
        }
    }
Beispiel #2
0
    ss_explicit_k module(S const& moduleName, int mode = RTLD_NOW)
        : m_hmodule(load(moduleName, mode))
    {
# ifdef STLSOFT_CF_EXCEPTION_SUPPORT
        if(NULL == m_hmodule)
        {
            STLSOFT_THROW_X(unix_exception("Cannot load module", errno));
        }
# endif /* STLSOFT_CF_EXCEPTION_SUPPORT */
    }
    /// \brief Releases an aquired lock on the semaphore, increasing the
    ///  semaphore's counter by one.
    void unlock()
    {
        UNIXSTL_ASSERT(NULL != m_sem);

        if(::sem_post(m_sem) < 0)
        {
#ifdef STLSOFT_CF_EXCEPTION_SUPPORT
            STLSOFT_THROW_X(synchronisation_exception("semaphore release failed", errno));
#endif /* STLSOFT_CF_EXCEPTION_SUPPORT */
        }
    }
Beispiel #4
0
    /// \brief Sets the state of the event to signalled
    void reset()
    {
        WINSTL_ASSERT(NULL != m_ev);

        if(!::ResetEvent(m_ev))
        {
#ifdef STLSOFT_CF_EXCEPTION_SUPPORT
            STLSOFT_THROW_X(synchronisation_exception("event reset operation failed", ::GetLastError()));
#endif /* STLSOFT_CF_EXCEPTION_SUPPORT */
        }
    }
    /// \brief Acquires a lock on the mutex, pending the thread until the lock is aquired
    ws_bool_t lock(ws_dword_t wait)
    {
        WINSTL_ASSERT(NULL != m_mx);

        DWORD const dwRes = ::WaitForSingleObject(m_mx, wait);

        if(WAIT_ABANDONED == dwRes)
        {
            m_bAbandoned = true;

            return true;
        }
        else
        {
            m_bAbandoned = false;

            if(WAIT_TIMEOUT == dwRes)
            {
                return false;
            }
            else
            {
                if(WAIT_OBJECT_0 != dwRes)
                {
                    DWORD const e = ::GetLastError();

#ifdef STLSOFT_CF_EXCEPTION_SUPPORT
# if STLSOFT_LEAD_VER >= 0x010a0000
                    STLSOFT_THROW_X(wait_failed_logic_exception(e, "mutex wait failed"));
# else /* ? STLSOFT_LEAD_VER >= 1.10 */
                    STLSOFT_THROW_X(synchronisation_exception("mutex wait failed", e));
# endif /* STLSOFT_LEAD_VER >= 1.10 */
#endif /* STLSOFT_CF_EXCEPTION_SUPPORT */
                }

                return true;
            }
        }
    }
Beispiel #6
0
    /// \brief Attempts to lock the mutex
    ///
    /// \return <b>true</b> if the mutex was aquired, or <b>false</b> if not.
    ///
    /// \exception unixstl::synchronisation_exception When compiling with exception support, this will throw
    /// unixstl::synchronisation_exception if the lock cannot be acquired for a reason
    /// other than a timeout (<code>EBUSY</code>). When compiling absent
    /// exception support, failure to acquire the lock (for any other
    /// reason) will be reflected in a non-zero return from get_error().
    bool try_lock()
    {
        m_error = ::pthread_mutex_trylock(m_mx);

        if(0 == m_error)
        {
            return true;
        }
        else
        {
#ifdef STLSOFT_CF_EXCEPTION_SUPPORT
            if(EBUSY != m_error)
            {
                STLSOFT_THROW_X(synchronisation_exception("Mutex try-lock failed", m_error));
            }
#endif /* STLSOFT_CF_EXCEPTION_SUPPORT */

            return false;
        }
    }
    /// \brief Attempts to lock the semaphore
    ///
    /// \return <b>true</b> if the semaphore was aquired, or <b>false</b> if not
    bool_type try_lock()
    {
        UNIXSTL_ASSERT(NULL != m_sem);

        int res =   ::sem_trywait(m_sem);

        if(0 == res)
        {
            return true;
        }
        else
        {
            if(EAGAIN != res)
            {
#ifdef STLSOFT_CF_EXCEPTION_SUPPORT
                STLSOFT_THROW_X(synchronisation_exception("semaphore wait failed", errno));
#endif /* STLSOFT_CF_EXCEPTION_SUPPORT */
            }
        }

        return false;
    }
    char const* check_description_a_()
    {
        if( NULL == m_description_a &&
            NULL != m_description)
        {
            int cch = ::WideCharToMultiByte(0, 0, m_description, -1, NULL, 0, NULL, NULL);

            m_description_a = static_cast<char*>(::CoTaskMemAlloc((1 + cch) * sizeof(char)));

            if(NULL == m_description_a)
            {
#ifdef STLSOFT_CF_THROW_BAD_ALLOC
                STLSOFT_THROW_X(stlsoft_ns_qual_std(bad_alloc)());
#endif /* STLSOFT_CF_THROW_BAD_ALLOC */
            }
            else
            {
                ::WideCharToMultiByte(0, 0, m_description, -1, m_description_a, 1 + cch, NULL, NULL);
            }
        }

        return (NULL == m_description_a) ? "" : m_description_a;
    }
    char const*
    make_message_(
        int e
    )
    {
#ifdef STLSOFT_USING_SAFE_STR_FUNCTIONS
        char        buff[1001];
        int const   e2  =   ::strerror_s(buff, e);
        char* const r   =   ::_strdup((0 == e2) ? buff : "unknown failure");

        if(NULL == r)
        {
            STLSOFT_THROW_X(std::bad_alloc());
        }

        context_ = r;

        return r;
#else /* ? STLSOFT_USING_SAFE_STR_FUNCTIONS */
        context_ = NULL;

        return ::strerror(e);
#endif /* STLSOFT_USING_SAFE_STR_FUNCTIONS */
    }
 /// Translates a CMemoryException* into a std::bad_alloc&
 static void handle(CMemoryException *)
 {
     STLSOFT_THROW_X(mfcstl_ns_qual_std(bad_alloc)());
 }
Beispiel #11
0
inline ws_uint64_t load_text_file_impl(S1 const& fileName, S2 &contents)
{
    typedef string_traits<S1>                               string_traits_t;

    STLSOFT_STATIC_ASSERT(sizeof(string_traits_t));     // Fires if S1 does not have a traits specialisation defined

    typedef string_traits<S2>                               string_traits2_t;

    STLSOFT_STATIC_ASSERT(sizeof(string_traits2_t));    // Fires if S2 does not have a traits specialisation defined

    typedef ss_typename_type_k string_traits_t::char_type   C;

    STLSOFT_STATIC_ASSERT(sizeof(C));                   // Fires if the traits is not correctly defined

    typedef ss_typename_type_k string_traits2_t::char_type  char_2_type;

    STLSOFT_STATIC_ASSERT(sizeof(char_2_type));         // Fires if the traits is not correctly defined

    typedef filesystem_traits<C>                            filesys_traits_t;

    STLSOFT_STATIC_ASSERT(sizeof(filesys_traits_t));    // Fires if no corresponding filesystem_traits defined

    scoped_handle<HANDLE>   h(  filesys_traits_t::create_file(  stlsoft_ns_qual(c_str_ptr)(fileName)
                                                            ,   GENERIC_READ
                                                            ,   FILE_SHARE_READ
                                                            ,   NULL
                                                            ,   OPEN_EXISTING
                                                            ,   0
                                                            ,   NULL)
                            ,   (void (STLSOFT_CDECL *)(HANDLE))&filesys_traits_t::close_handle // This cast required by VC++ 5
                            ,   INVALID_HANDLE_VALUE);

    if(INVALID_HANDLE_VALUE == h.get())
    {
        STLSOFT_THROW_X(windows_exception("File does not exist", ::GetLastError()));
    }

    ws_uint64_t             size    =   filesys_traits_t::get_file_size(h.get());

    if( 0 != size &&
        static_cast<ws_uint64_t>(~0) != size)
    {
        if(size > 0xFFFFFFFF)
        {
            STLSOFT_THROW_X(winstl_ns_qual_std(out_of_range)("Cannot read in files larger than 4GB"));
        }
        else
        {
// TODO: Catch the out-of-memory exception and translate to a std::out_of_range()

            typedef ::stlsoft::auto_buffer_old< char_2_type
                                            ,   processheap_allocator<char_2_type>
                                            ,   1024
                                            >                   buffer_t;

            buffer_t    buffer(static_cast<ss_typename_type_k buffer_t::size_type>(size));
            DWORD       dw;

            if(!::ReadFile(h.get(), &buffer[0], buffer.size(), &dw, NULL))
            {
                STLSOFT_THROW_X(windows_exception("Read operation failed", ::GetLastError()));
            }
            else
            {
                contents.assign(&buffer[0], dw);

                return size;
            }
        }
    }

    return 0;
}