STL map and unicode

Discussion in 'C++' started by Vincent RICHOMME, Feb 1, 2007.

  1. Hi,

    I would like to use a hashtable to associate a windows unicode string
    (define as a ulong *) to a list.
    So first I try this :

    typedef std::list<FunctionInfo> FuncList;
    FuncList g_FuncList;

    typedef std::map<LPWSTR, FuncList> ModuleList;
    ModuleList g_ModuleList;


    void Hook_API( LPWSTR p_wszModuleName,
    LPWSTR p_wszFunctionName,
    PROC p_pfnNewProc
    )
    {
    ModuleList::iterator l_it;

    l_it = g_ModuleList.find( (LPWSTR)p_wszModuleName );
    if (l_it == g_ModuleList.end() ){
    ...
    }
    }

    when I try this if I call three times my function with the same
    parameter (L"coredll.dll" for instance) I will have
    three keys in my hashtable

    Hook_API(L"coredll.dll", "func1", NULL);
    Hook_API(L"coredll.dll", "func2", NULL);
    Hook_API(L"coredll.dll", "func3", NULL);

    So I should have only one key in my hash table (coredll.dll) but it's
    not the case


    I think it's because map considers LPWSTR as a pointer and not as a
    string. So LPWSTR is always different since address is different.

    Maybe I should use std::string but in this case how to do with unicode
    string.
     
    Vincent RICHOMME, Feb 1, 2007
    #1
    1. Advertising

  2. Vincent RICHOMME

    Ondra Holub Guest

    Vincent RICHOMME napsal:
    > Hi,
    >
    > I would like to use a hashtable to associate a windows unicode string
    > (define as a ulong *) to a list.
    > So first I try this :
    >
    > typedef std::list<FunctionInfo> FuncList;
    > FuncList g_FuncList;
    >
    > typedef std::map<LPWSTR, FuncList> ModuleList;
    > ModuleList g_ModuleList;
    >
    >
    > void Hook_API( LPWSTR p_wszModuleName,
    > LPWSTR p_wszFunctionName,
    > PROC p_pfnNewProc
    > )
    > {
    > ModuleList::iterator l_it;
    >
    > l_it = g_ModuleList.find( (LPWSTR)p_wszModuleName );
    > if (l_it == g_ModuleList.end() ){
    > ...
    > }
    > }
    >
    > when I try this if I call three times my function with the same
    > parameter (L"coredll.dll" for instance) I will have
    > three keys in my hashtable
    >
    > Hook_API(L"coredll.dll", "func1", NULL);
    > Hook_API(L"coredll.dll", "func2", NULL);
    > Hook_API(L"coredll.dll", "func3", NULL);
    >
    > So I should have only one key in my hash table (coredll.dll) but it's
    > not the case
    >
    >
    > I think it's because map considers LPWSTR as a pointer and not as a
    > string. So LPWSTR is always different since address is different.
    >
    > Maybe I should use std::string but in this case how to do with unicode
    > string.


    You have to specify comparing function for map. With the default
    comparing function are compared pointers (L"hello" and L"hello" may or
    need not be on the same place in memory, so pointers may or need not
    to be same):

    struct Comparator
    {
    bool operator()(const LPWSTR s1, const LPWSTR s2)
    {
    // here implement your function. I do not know LPWSTR, because
    I do not use windows
    // but for char* it would look this way:
    // return strcmp(s1, s2) < 0;
    // So simply replace strcmp with comparing function for LPWSTR
    }
    };

    typedef std::map<LPWSTR, FuncList, Comparator> ModuleList;
     
    Ondra Holub, Feb 1, 2007
    #2
    1. Advertising

  3. Vincent RICHOMME

    Satish Guest

    On Feb 1, 1:28 pm, Vincent RICHOMME <> wrote:
    > Hi,
    >
    > I would like to use a hashtable to associate a windows unicode string
    > (define as a ulong *) to a list.
    > So first I try this :
    >
    > typedef std::list<FunctionInfo> FuncList;
    > FuncList g_FuncList;
    >
    > typedef std::map<LPWSTR, FuncList> ModuleList;
    > ModuleList g_ModuleList;
    >
    > void Hook_API( LPWSTR p_wszModuleName,
    > LPWSTR p_wszFunctionName,
    > PROC p_pfnNewProc
    > )
    > {
    > ModuleList::iterator l_it;
    >
    > l_it = g_ModuleList.find( (LPWSTR)p_wszModuleName );
    > if (l_it == g_ModuleList.end() ){
    > ...
    > }
    >
    > }
    >
    > when I try this if I call three times my function with the same
    > parameter (L"coredll.dll" for instance) I will have
    > three keys in my hashtable
    >
    > Hook_API(L"coredll.dll", "func1", NULL);
    > Hook_API(L"coredll.dll", "func2", NULL);
    > Hook_API(L"coredll.dll", "func3", NULL);
    >
    > So I should have only one key in my hash table (coredll.dll) but it's
    > not the case
    >
    > I think it's because map considers LPWSTR as a pointer and not as a
    > string. So LPWSTR is always different since address is different.
    >
    > Maybe I should use std::string but in this case how to do with unicode
    > string.


    You should declare a static/global/member variable and declare
    L"coredll.dll"/
    and pass this variable each time instead of explicitly calling like
    L"coredll.dll". Something like calling twice
    Hook_API(L"coredll.dll", "func2", NULL); you are passing 2 different
    pointers each time. LPWSTR is Long pointer to wide string is a macro
    for wchar_t*. You could try using wstring. Check a related article
    at
    http://groups.google.com/group/borl...977de386b7106/87f9968c341cf39#87f9968c341cf39
     
    Satish, Feb 1, 2007
    #3
  4. On Feb 2, 1:28 am, Vincent RICHOMME <> wrote:
    > Hi,
    >
    > I would like to use a hashtable to associate a windows unicode string
    > (define as a ulong *) to a list.
    > So first I try this :
    >
    > typedef std::list<FunctionInfo> FuncList;
    > FuncList g_FuncList;
    >
    > typedef std::map<LPWSTR, FuncList> ModuleList;
    > ModuleList g_ModuleList;
    >
    > void Hook_API( LPWSTR p_wszModuleName,
    > LPWSTR p_wszFunctionName,
    > PROC p_pfnNewProc
    > )
    > {
    > ModuleList::iterator l_it;
    >
    > l_it = g_ModuleList.find( (LPWSTR)p_wszModuleName );
    > if (l_it == g_ModuleList.end() ){
    > ...
    > }
    >
    > }
    >
    > when I try this if I call three times my function with the same
    > parameter (L"coredll.dll" for instance) I will have
    > three keys in my hashtable
    >
    > Hook_API(L"coredll.dll", "func1", NULL);
    > Hook_API(L"coredll.dll", "func2", NULL);
    > Hook_API(L"coredll.dll", "func3", NULL);
    >
    > So I should have only one key in my hash table (coredll.dll) but it's
    > not the case
    >
    > I think it's because map considers LPWSTR as a pointer and not as a
    > string. So LPWSTR is always different since address is different.
    >
    > Maybe I should use std::string but in this case how to do with unicode
    > string.


    The simplest thing is to use std::wstring which uses wchar_t (16 bit
    on Windows).

    You have a lot of C style code in there. This line here:

    l_it = g_ModuleList.find( (LPWSTR)p_wszModuleName );

    Is particularly nasty. Why the C style cast on the type which is
    already LPWSTR? This is a really bad habit to get into as you are
    subverting the type system and you lose many of the benefits of C++
    stronger typing.

    Lost of Microsoft's API calls are not const correct (they seem to be
    trying to change this, but it's not 100% yet). That's no reason for
    you to copy them though.

    > void Hook_API( LPWSTR p_wszModuleName,
    > LPWSTR p_wszFunctionName,
    > PROC p_pfnNewProc
    > )


    Here you should really be using LPCWSTR (I think it is) or at least
    this:

    void Hook_API( const LPWSTR p_wszModuleName,
    const LPWSTR p_wszFunctionName,
    PROC p_pfnNewProc
    );

    Better yet would be this:

    void Hook_API( const std::wstring &moduleName, const std::wstring
    &functionName, PROC newProc );

    The Hungarian notation that you use was originally meant to help
    overcome inadequacies of the type system. There's no real reason to
    use them in languages with better type systems like C++.


    K
     
    =?iso-8859-1?q?Kirit_S=E6lensminde?=, Feb 2, 2007
    #4
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Bart Kevelham

    char* and STL map

    Bart Kevelham, Oct 6, 2003, in forum: C++
    Replies:
    3
    Views:
    7,726
    Jerry Coffin
    Oct 7, 2003
  2. Marcus
    Replies:
    2
    Views:
    591
    Marcus
    Dec 9, 2005
  3. Replies:
    2
    Views:
    556
    klaus hoffmann
    Feb 22, 2006
  4. kl
    Replies:
    7
    Views:
    1,291
    James Kanze
    Jan 1, 2008
  5. Luca Risolia

    STL map to STL vector

    Luca Risolia, Jan 13, 2014, in forum: C++
    Replies:
    32
    Views:
    375
    Seungbeom Kim
    Jan 18, 2014
Loading...

Share This Page