summaryrefslogtreecommitdiff
path: root/src/nativeresources
diff options
context:
space:
mode:
authorKyungwoo Lee <kyulee@microsoft.com>2015-12-03 14:26:05 -0800
committerKyungwoo Lee <kyulee@microsoft.com>2015-12-03 20:41:18 -0800
commit1d34f6293740f4f79f8b362c2d605fa2a527d538 (patch)
treea716d441f4449582b25bf2de9b264ba56fd8ee19 /src/nativeresources
parent0bdc646c5955ca0c735a3976d01969b246e848ef (diff)
downloadcoreclr-1d34f6293740f4f79f8b362c2d605fa2a527d538.tar.gz
coreclr-1d34f6293740f4f79f8b362c2d605fa2a527d538.tar.bz2
coreclr-1d34f6293740f4f79f8b362c2d605fa2a527d538.zip
Refactoring resource string
This pulls out resource string handling out of mscorrc into top level. The scripts (awk) are now parameterized to generate a unique string table for the given name. Added resourcestring.cpp to create an API "LoadResourceString". Added a few macros into resourcestring.h, which are used for definition/uses of the string table.
Diffstat (limited to 'src/nativeresources')
-rw-r--r--src/nativeresources/.gitmirror1
-rw-r--r--src/nativeresources/CMakeLists.txt9
-rw-r--r--src/nativeresources/processrc.awk64
-rw-r--r--src/nativeresources/rctocpp.awk84
-rw-r--r--src/nativeresources/rctopo.awk21
-rw-r--r--src/nativeresources/resourcestring.cpp63
-rw-r--r--src/nativeresources/resourcestring.h33
7 files changed, 275 insertions, 0 deletions
diff --git a/src/nativeresources/.gitmirror b/src/nativeresources/.gitmirror
new file mode 100644
index 0000000000..f507630f94
--- /dev/null
+++ b/src/nativeresources/.gitmirror
@@ -0,0 +1 @@
+Only contents of this folder, excluding subfolders, will be mirrored by the Git-TFS Mirror. \ No newline at end of file
diff --git a/src/nativeresources/CMakeLists.txt b/src/nativeresources/CMakeLists.txt
new file mode 100644
index 0000000000..5bc326492a
--- /dev/null
+++ b/src/nativeresources/CMakeLists.txt
@@ -0,0 +1,9 @@
+project(nativeresourcestring)
+
+add_compile_options(-fPIC)
+
+add_library(nativeresourcestring
+ STATIC
+ resourcestring.cpp
+)
+
diff --git a/src/nativeresources/processrc.awk b/src/nativeresources/processrc.awk
new file mode 100644
index 0000000000..1632753956
--- /dev/null
+++ b/src/nativeresources/processrc.awk
@@ -0,0 +1,64 @@
+# Parse string resources from Windows native resource file
+# and pass them to the writestringentry function that
+# is responsible for writing the resource id and string
+# to a platform specific resource file.
+# A script containing this function needs to be specified
+# using the -f command line parameter before this script.
+
+BEGIN {
+ inStringTable = 0;
+ inBeginEnd = 0;
+ arrayName = "nativeStringResourceArray_" name;
+ tableName = "nativeStringResourceTable_" name;
+ writeheader(arrayName, tableName);
+}
+{
+ if ($1 == "STRINGTABLE" && $2 == "DISCARDABLE")
+ {
+ inStringTable = 1;
+ }
+ else if ($1 == "BEGIN")
+ {
+ inBeginEnd = inStringTable;
+ }
+ else if (inBeginEnd && $1 == "END")
+ {
+ inBeginEnd = 0;
+ inStringTable = 0;
+ }
+ else if (inBeginEnd && $1 != "")
+ {
+ # combine all items until the first string and remove them
+ # from the line
+ i = 1
+ expression = ""
+ # string starts with either a quote or L followed by a quote
+ while (substr($i, 1, 1) != "\"" && substr($i, 1, 2) != "L\"")
+ {
+ # some of the resource IDs contain cast to HRESULT
+ gsub(/\(HRESULT\)/, "", $i);
+ # some of the resource IDs have trailing L
+ gsub(/L/, "", $i);
+ expression = expression $i;
+ $i="";
+ i++;
+ }
+ # evaluate the resource ID expression
+ cmd = "echo $(("expression"))";
+ cmd | getline var;
+ close(cmd);
+ # in case shell returned the result as a string, ensure the var has numeric type
+ var = var + 0;
+
+ # remove the L prefix from strings
+ gsub(/L"/, "\"", $0);
+ # join strings "..." "..." into one
+ gsub(/" +"/, "", $0);
+
+ # write the resource entry to the target file
+ writestringentry(var, $0);
+ }
+}
+END {
+ writefooter(arrayName, tableName);
+}
diff --git a/src/nativeresources/rctocpp.awk b/src/nativeresources/rctocpp.awk
new file mode 100644
index 0000000000..e631021b35
--- /dev/null
+++ b/src/nativeresources/rctocpp.awk
@@ -0,0 +1,84 @@
+# Convert string resources from Windows native resource file to a C++
+# source file with an array of structs representing the resources.
+
+BEGIN {
+ numEntries = 0;
+}
+
+# Takes a number and returns a string corresponding to its hex
+# representation. A string representation that has fewer than 8
+# characters (not including the '0x' prefix) is padded with 0's
+# to make it 8 characters.
+# Example: an input of 49 yields "0x00000031".
+function numberToHexString(number)
+{
+ quotient = number;
+
+ hexString = "";
+ for (digitCount = 0; digitCount < 8; digitCount++)
+ {
+ remainder = quotient % 16;
+ quotient = int(quotient / 16);
+ hexString = sprintf("%x"hexString, remainder);
+ }
+
+ hexString = "0x" hexString;
+ return hexString;
+}
+
+# Add each entry that is in our associative array of entries to the
+# C++ array we are building. The C++ array will be ordered by the
+# resourceId (lowest to highest) to facilitate quick lookups.
+function writesortedentries()
+{
+ for (entry in resourceArray)
+ {
+ # Write the entries to the C++ array ordered by the ID.
+ printf " {%s,%s},\n", entry, resourceArray[entry] | "sort";
+ }
+
+ # Close the pipe to ensure that the data is written now.
+ close("sort");
+}
+
+# Write entry for a string resource
+# This is called for each entry. Because we want to write them in
+# sorted order once all the entries have come in, for now we just
+# store each entry in an associative array.
+function writestringentry(id, str)
+{
+ numEntries++;
+
+ # Use the string representation of the ID as the array index
+ # because the precision of numeric indices can be lost during
+ # the number -> string -> number conversions that would occur
+ # if numeric indices are used.
+ resourceArray[numberToHexString(id)] = str;
+}
+
+# Write file header and begin the array we will populate with the resources.
+function writeheader(arrayName, tableName)
+{
+ print "// This code was generated by rctocpp.awk and is not meant to be modified manually."
+ print "#include <resourcestring.h>";
+ print "";
+ print "extern const NativeStringResourceTable " tableName ";";
+ print "const NativeStringResource " arrayName "[] = {";
+}
+
+# Write file footer
+# This function is called after all of the entries have been given to
+# writestringentry. Because we know there are no more entries, we can
+# now write all the entries we received so far when this is called.
+# After we have written all the entries, we close the array and add a
+# constant for the size of the array for convenience.
+function writefooter(arrayName, tableName)
+{
+ writesortedentries();
+ print "};";
+ print "";
+
+ print "const NativeStringResourceTable " tableName " = {";
+ print numEntries ",";
+ print arrayName "};";
+}
diff --git a/src/nativeresources/rctopo.awk b/src/nativeresources/rctopo.awk
new file mode 100644
index 0000000000..5229585ff5
--- /dev/null
+++ b/src/nativeresources/rctopo.awk
@@ -0,0 +1,21 @@
+# Convert string resources from Windows native resource file to the
+# input format of the gettext toolchain.
+
+# Write entry for a string resource
+function writestringentry(id, str)
+{
+ idAsStr = sprintf("%X", id);
+ print "msgid \""idAsStr"\"";
+ print "msgstr" str;
+ print "";
+}
+
+# Write file header
+function writeheader()
+{
+}
+
+# Write file footer
+function writefooter()
+{
+}
diff --git a/src/nativeresources/resourcestring.cpp b/src/nativeresources/resourcestring.cpp
new file mode 100644
index 0000000000..75fb1ececd
--- /dev/null
+++ b/src/nativeresources/resourcestring.cpp
@@ -0,0 +1,63 @@
+//
+// Copyright (c) Microsoft. All rights reserved.
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
+//
+
+
+#include <stdio.h>
+#include <utilcode.h>
+#include "resourcestring.h"
+
+static int CompareNativeStringResources(const void *a, const void *b)
+{
+ unsigned int resourceIdA = ((NativeStringResource*)a)->resourceId;
+ unsigned int resourceIdB = ((NativeStringResource*)b)->resourceId;
+
+ if (resourceIdA < resourceIdB)
+ return -1;
+
+ if (resourceIdA == resourceIdB)
+ return 0;
+
+ return 1;
+}
+
+int LoadNativeStringResource(const NativeStringResourceTable &nativeStringResourceTable, unsigned int iResourceID, WCHAR* szBuffer, int iMax, int *pcwchUsed)
+{
+ int len = 0;
+ if (szBuffer && iMax)
+ {
+ // Search the sorted set of resources for the ID we're interested in.
+ NativeStringResource searchEntry = {iResourceID, NULL};
+ NativeStringResource *resourceEntry = (NativeStringResource*)bsearch(
+ &searchEntry,
+ nativeStringResourceTable.table,
+ nativeStringResourceTable.size,
+ sizeof(NativeStringResource),
+ CompareNativeStringResources);
+
+ if (resourceEntry != NULL)
+ {
+ len = PAL_GetResourceString(NULL, resourceEntry->resourceString, szBuffer, iMax);
+ }
+ else
+ {
+ // The resource ID wasn't found in our array. Fall back on returning the ID as a string.
+ len = _snwprintf(szBuffer, iMax - 1, W("[Undefined resource string ID:0x%X]"), iResourceID);
+ if ((len < 0) || (len == (iMax - 1)))
+ {
+ // Add string terminator if the result of _snwprintf didn't fit the buffer.
+ szBuffer[iMax - 1] = W('\0');
+ len = iMax - 1;
+ }
+ }
+ }
+
+ if (pcwchUsed)
+ {
+ *pcwchUsed = len;
+ }
+
+ return S_OK;
+}
+
diff --git a/src/nativeresources/resourcestring.h b/src/nativeresources/resourcestring.h
new file mode 100644
index 0000000000..1545b3c48f
--- /dev/null
+++ b/src/nativeresources/resourcestring.h
@@ -0,0 +1,33 @@
+//
+// Copyright (c) Microsoft. All rights reserved.
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
+//
+
+#ifndef __RESOURCE_STRING_H_
+#define __RESOURCE_STRING_H_
+
+// Struct to contain a resource ID and its corresponding
+// English language string.
+struct NativeStringResource
+{
+ unsigned int resourceId;
+ const char* resourceString;
+};
+
+struct NativeStringResourceTable
+{
+ const int size;
+ const NativeStringResource *table;
+};
+
+int LoadNativeStringResource(const NativeStringResourceTable &nativeStringResourceTable, unsigned int iResourceID, char16_t* szBuffer, int iMax, int *pcwchUsed);
+
+#define CONCAT(a, b) a ## b
+
+#define NATIVE_STRING_RESOURCE_TABLE(name) CONCAT(nativeStringResourceTable_, name)
+
+#define DECLARE_NATIVE_STRING_RESOURCE_TABLE(name) \
+ extern const NativeStringResourceTable NATIVE_STRING_RESOURCE_TABLE(name)
+
+#endif // __RESOURCE_STRING_H_
+