title: How to read STRING TABLE resources for given language into map
body: <p>I have translated strings for multiple languages in vs resource <code>.rc</code> files stored in <code>STRINGTABLE</code></p>
  
  <pre><code>//english.rc
  
  #pragma code_page(65001)
  #define APSTUDIO_READONLY_SYMBOLS
  #include "afxres.h"
  #undef APSTUDIO_READONLY_SYMBOLS
  #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
  
  LANGUAGE LANG_ENGLISH, SUBLANG_NEUTRAL
  
  STRINGTABLE
  BEGIN
      1000                    "SOME TEXT"
      7777                    "SOME TEXT"
  END
  #endif
  
  //danish.rc
  #pragma code_page(65001)
  #define APSTUDIO_READONLY_SYMBOLS
  #include "afxres.h"
  #undef APSTUDIO_READONLY_SYMBOLS
  #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
  LANGUAGE LANG_DANISH, SUBLANG_NEUTRAL
  
  STRINGTABLE
  BEGIN
      1001                    "SOME TEXT IN DANISH"
      7777                    "SOME TEXT IN DANISH"
  END
  #endif
  </code></pre>
  
  <p>I want to load those resources to the map of [languageId : [(resourceId: value),...],...]</p>
  
  <p><code>std::map&lt;long /*languageId*/, std::map&lt;long /*resource id (1000, 7777, 1001)*/, std::string /*value*/&gt;&gt;</code> </p>
  
  <p>I do not know how many resources are in the <code>.rc</code> files, I do not know resource Ids either (I expect there is some way to get all ids from the file, but I haven't found a way to do that so far)</p>
  
  <p><strong>What I tried</strong></p>
  
  <p>Iterating through resources via callback. </p>
  
  <pre><code>#include &lt;iostream&gt;
  #include &lt;windows.h&gt;
  #include &lt;map&gt;
  
  BOOL EnumResourceLanguagesCallback(HMODULE applicationModule, LPCTSTR resourceType, LPCTSTR resourceName, WORD languageId, std::map&lt;long /*languageId*/, std::map&lt;long /*resource id (e.g. 1000, 7777, 1001)*/, std::string /*resource value*/&gt;&gt; * pResources)
  {
      HRSRC hResInfo = FindResourceEx(applicationModule, resourceType, resourceName, languageId);
      HGLOBAL hData = LoadResource(0, hResInfo);
  
      std::wstring values;
      values.assign((wchar_t*)LockResource(hData), SizeofResource(applicationModule, hResInfo));
      /* values string is either empty or contains garbage or sometimes partial string with some of the resources in the rc file - depends on the amount of resources in rc file*/
      return TRUE;
  }
  
  
  BOOL EnumResourceNamesCallback(HMODULE applicationModule, LPCTSTR resourceType, LPTSTR resourceName, std::map&lt;long /*languageId*/, std::map&lt;long /*resource id (e.g. 1000, 7777, 1001)*/, std::string /*resource value*/&gt;&gt; *pResources)
  {
      return EnumResourceLanguages(applicationModule, resourceType, resourceName, (ENUMRESLANGPROC)EnumResourceLanguagesCallback, reinterpret_cast&lt;LONG_PTR&gt;(pResources));
  }
  
  int main()
  {
      std::map&lt;long /*languageId*/, std::map&lt;long /*resource id (e.g. 1000, 7777, 1001)*/, std::string /*resource value*/&gt;&gt; resources;
  
      EnumResourceNames(::GetModuleHandleA(nullptr), RT_STRING, (ENUMRESNAMEPROC)EnumResourceNamesCallback, reinterpret_cast&lt;LONG_PTR&gt;(&amp;resources));
  }
  </code></pre>
  
  <p>This gave me all handles to resources with ability to call LoadResource &amp; LockResource, but from here it is unclear to me how to get </p>
  
  <ol>
  <li>List of available resource ids for a given resource handle</li>
  <li>Actually get a value of a resource </li>
  </ol>
  
  <p>There seems to be something in the <code>wchar_t *data</code> after locking resource, but it doesn't seem to be structured in any way for <code>STRINGTABLE</code>, maybe it would work for binary resource, but <code>STRINGTABLE</code> format doesn't seem to be parsable</p>
  
  <p><strong>What else I tried</strong></p>
  
  <p>Just calling LoadString, but for that </p>
  
  <ol>
  <li>I can't specify language (and I can't mess with system or application locale) </li>
  <li>I do not know how to get available resource ids</li>
  </ol>
  
  <p>EDIT:
  Added more investigation towards getting data via LockResource</p>