Mercurial > hg > orthanc-stone
changeset 39:9ee7e2f5f1a3
sync
author | Sebastien Jodogne <s.jodogne@gmail.com> |
---|---|
date | Wed, 21 Dec 2016 14:19:38 +0100 |
parents | bfce0add15f2 |
children | 7207a407bcd8 |
files | Framework/Widgets/TestCairoWidget.cpp Resources/CMake/CairoConfiguration.cmake Resources/CMake/PixmanConfiguration.cmake Resources/Graveyard/Toolbox/DicomDataset.cpp Resources/Graveyard/Toolbox/DicomDataset.h Resources/Orthanc/Core/SystemToolbox.cpp Resources/Orthanc/Core/SystemToolbox.h Resources/Orthanc/Core/Toolbox.cpp Resources/Orthanc/Core/Toolbox.h Resources/Orthanc/Core/WebServiceParameters.cpp Resources/Orthanc/Plugins/Samples/Common/DicomPath.cpp Resources/Orthanc/Plugins/Samples/Common/DicomPath.h Resources/Orthanc/Resources/CMake/BoostConfiguration.cmake |
diffstat | 13 files changed, 507 insertions(+), 48 deletions(-) [+] |
line wrap: on
line diff
--- a/Framework/Widgets/TestCairoWidget.cpp Mon Dec 19 12:55:14 2016 +0100 +++ b/Framework/Widgets/TestCairoWidget.cpp Wed Dec 21 14:19:38 2016 +0100 @@ -32,7 +32,7 @@ #include "TestCairoWidget.h" -#include "../../Resources/Orthanc/Core/Toolbox.h" +#include "../../Resources/Orthanc/Core/SystemToolbox.h" #include <stdio.h> @@ -51,7 +51,7 @@ NotifyChange(); - Orthanc::Toolbox::USleep(25000); + Orthanc::SystemToolbox::USleep(25000); }
--- a/Resources/CMake/CairoConfiguration.cmake Mon Dec 19 12:55:14 2016 +0100 +++ b/Resources/CMake/CairoConfiguration.cmake Wed Dec 21 14:19:38 2016 +0100 @@ -193,6 +193,10 @@ # Disable vectorized instructions when targeting archicture-independent PNaCl set(CAIRO_DEFINITIONS "${CAIRO_DEFINITIONS};HAVE_STDINT_H=1;CAIRO_HAS_PTHREAD=1;HAVE_UINT64_T=1") + elseif (${CMAKE_SYSTEM_NAME} STREQUAL "Emscripten") + # Disable vectorized instructions and threading if targeting asm.js + set(CAIRO_DEFINITIONS "${CAIRO_DEFINITIONS};HAVE_STDINT_H=1;CAIRO_HAS_PTHREAD=0;CAIRO_NO_MUTEX=1;HAVE_UINT64_T=1") + elseif (CMAKE_COMPILER_IS_GNUCXX OR CMAKE_SYSTEM_NAME STREQUAL "Darwin")
--- a/Resources/CMake/PixmanConfiguration.cmake Mon Dec 19 12:55:14 2016 +0100 +++ b/Resources/CMake/PixmanConfiguration.cmake Wed Dec 21 14:19:38 2016 +0100 @@ -81,7 +81,23 @@ endif() - if (CMAKE_SYSTEM_NAME STREQUAL "Windows") + ########################## + ## Portable Google NaCl + ########################## + + if (CMAKE_SYSTEM_NAME STREQUAL "PNaCl") + # No hardware acceleration + set(PIXMAN_DEFINITIONS "${PIXMAN_DEFINITIONS};TLS=__thread") + + elseif (CMAKE_SYSTEM_NAME STREQUAL "Emscripten") + ########################## + ## Emscripten (asm.js) + ########################## + + # No threading support + set(PIXMAN_DEFINITIONS "${PIXMAN_DEFINITIONS};PIXMAN_NO_TLS=1;HAVE_GCC_VECTOR_EXTENSIONS") + + elseif (CMAKE_SYSTEM_NAME STREQUAL "Windows") ########################## ## Windows 32 or 64 @@ -183,14 +199,6 @@ ${PIXMAN_SOURCES_DIR}/pixman/pixman-arm-simd.c ) - ########################## - ## Portable Google NaCl - ########################## - - elseif (CMAKE_SYSTEM_NAME STREQUAL "PNaCl") - # No hardware acceleration - set(PIXMAN_DEFINITIONS "${PIXMAN_DEFINITIONS};TLS=__thread") - else() message(FATAL_ERROR "Support your platform here") endif()
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/Resources/Graveyard/Toolbox/DicomDataset.cpp Wed Dec 21 14:19:38 2016 +0100 @@ -0,0 +1,315 @@ +/** + * Stone of Orthanc + * Copyright (C) 2012-2016 Sebastien Jodogne, Medical Physics + * Department, University Hospital of Liege, Belgium + * + * This program is free software: you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation, either version 3 of the + * License, or (at your option) any later version. + * + * In addition, as a special exception, the copyright holders of this + * program give permission to link the code of its release with the + * OpenSSL project's "OpenSSL" library (or with modified versions of it + * that use the same license as the "OpenSSL" library), and distribute + * the linked executables. You must obey the GNU General Public License + * in all respects for all of the code used other than "OpenSSL". If you + * modify file(s) with this exception, you may extend this exception to + * your version of the file(s), but you are not obligated to do so. If + * you do not wish to do so, delete this exception statement from your + * version. If you delete this exception statement from all source files + * in the program, then also delete it here. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + **/ + + +#include "DicomDataset.h" + +#include "../../Resources/Orthanc/Core/OrthancException.h" +#include "../../Resources/Orthanc/Core/Logging.h" +#include "../../Resources/Orthanc/Core/Toolbox.h" + +#include <boost/lexical_cast.hpp> +#include <json/value.h> +#include <json/reader.h> + +namespace OrthancStone +{ + static uint16_t GetCharValue(char c) + { + if (c >= '0' && c <= '9') + return c - '0'; + else if (c >= 'a' && c <= 'f') + return c - 'a' + 10; + else if (c >= 'A' && c <= 'F') + return c - 'A' + 10; + else + return 0; + } + + + static uint16_t GetHexadecimalValue(const char* c) + { + return ((GetCharValue(c[0]) << 12) + + (GetCharValue(c[1]) << 8) + + (GetCharValue(c[2]) << 4) + + GetCharValue(c[3])); + } + + + static DicomDataset::Tag ParseTag(const std::string& tag) + { + if (tag.size() == 9 && + isxdigit(tag[0]) && + isxdigit(tag[1]) && + isxdigit(tag[2]) && + isxdigit(tag[3]) && + (tag[4] == '-' || tag[4] == ',') && + isxdigit(tag[5]) && + isxdigit(tag[6]) && + isxdigit(tag[7]) && + isxdigit(tag[8])) + { + uint16_t group = GetHexadecimalValue(tag.c_str()); + uint16_t element = GetHexadecimalValue(tag.c_str() + 5); + return std::make_pair(group, element); + } + else if (tag.size() == 8 && + isxdigit(tag[0]) && + isxdigit(tag[1]) && + isxdigit(tag[2]) && + isxdigit(tag[3]) && + isxdigit(tag[4]) && + isxdigit(tag[5]) && + isxdigit(tag[6]) && + isxdigit(tag[7])) + { + uint16_t group = GetHexadecimalValue(tag.c_str()); + uint16_t element = GetHexadecimalValue(tag.c_str() + 4); + return std::make_pair(group, element); + } + else + { + throw Orthanc::OrthancException(Orthanc::ErrorCode_BadFileFormat); + } + } + + void DicomDataset::Parse(const std::string& content) + { + Json::Value json; + Json::Reader reader; + if (!reader.parse(content, json)) + { + throw Orthanc::OrthancException(Orthanc::ErrorCode_BadFileFormat); + } + + Parse(json); + } + + + void DicomDataset::Parse(const Json::Value& content) + { + if (content.type() != Json::objectValue) + { + throw Orthanc::OrthancException(Orthanc::ErrorCode_BadFileFormat); + } + + Json::Value::Members members = content.getMemberNames(); + for (size_t i = 0; i < members.size(); i++) + { + Tag tag = ParseTag(members[i]); + + const Json::Value& item = content[members[i]]; + + if (item.type() != Json::objectValue || + !item.isMember("Type") || + !item.isMember("Value") || + !item.isMember("Name") || + item["Type"].type() != Json::stringValue || + item["Name"].type() != Json::stringValue) + { + throw Orthanc::OrthancException(Orthanc::ErrorCode_BadFileFormat); + } + + if (item["Type"].asString() == "String") + { + if (item["Value"].type() == Json::stringValue) + { + values_[tag] = item["Value"].asString(); + } + else + { + throw Orthanc::OrthancException(Orthanc::ErrorCode_BadFileFormat); + } + } + } + } + + + DicomDataset::DicomDataset(OrthancPlugins::IOrthancConnection& orthanc, + const std::string& instanceId) + { + std::string content; + orthanc.RestApiGet(content, "/instances/" + instanceId + "/tags"); + + Parse(content); + } + + + std::string DicomDataset::GetStringValue(const Tag& tag) const + { + Values::const_iterator it = values_.find(tag); + + if (it == values_.end()) + { + LOG(ERROR) << "Trying to access a DICOM tag that is not set in a DICOM dataset"; + throw Orthanc::OrthancException(Orthanc::ErrorCode_InexistentItem); + } + else + { + return it->second; + } + } + + + std::string DicomDataset::GetStringValue(const Tag& tag, + const std::string& defaultValue) const + { + Values::const_iterator it = values_.find(tag); + + if (it == values_.end()) + { + return defaultValue; + } + else + { + return it->second; + } + } + + + float DicomDataset::GetFloatValue(const Tag& tag) const + { + try + { + return boost::lexical_cast<float>(Orthanc::Toolbox::StripSpaces(GetStringValue(tag))); + } + catch (boost::bad_lexical_cast&) + { + LOG(ERROR) << "Trying to access a DICOM tag that is not a float"; + throw Orthanc::OrthancException(Orthanc::ErrorCode_BadFileFormat); + } + } + + + double DicomDataset::GetDoubleValue(const Tag& tag) const + { + try + { + return boost::lexical_cast<double>(Orthanc::Toolbox::StripSpaces(GetStringValue(tag))); + } + catch (boost::bad_lexical_cast&) + { + LOG(ERROR) << "Trying to access a DICOM tag that is not a float"; + throw Orthanc::OrthancException(Orthanc::ErrorCode_BadFileFormat); + } + } + + + int DicomDataset::GetIntegerValue(const Tag& tag) const + { + try + { + return boost::lexical_cast<int>(Orthanc::Toolbox::StripSpaces(GetStringValue(tag))); + } + catch (boost::bad_lexical_cast&) + { + LOG(ERROR) << "Trying to access a DICOM tag that is not an integer"; + throw Orthanc::OrthancException(Orthanc::ErrorCode_BadFileFormat); + } + } + + + unsigned int DicomDataset::GetUnsignedIntegerValue(const Tag& tag) const + { + int v = GetIntegerValue(tag); + + if (v < 0) + { + throw Orthanc::OrthancException(Orthanc::ErrorCode_BadFileFormat); + } + else + { + return static_cast<unsigned int>(v); + } + } + + + void DicomDataset::GetVectorValue(Vector& vector, + const Tag& tag) const + { + if (!GeometryToolbox::ParseVector(vector, Orthanc::Toolbox::StripSpaces(GetStringValue(tag)))) + { + LOG(ERROR) << "Trying to access a DICOM tag that is not a vector"; + throw Orthanc::OrthancException(Orthanc::ErrorCode_BadFileFormat); + } + } + + + void DicomDataset::GetVectorValue(Vector& vector, + const Tag& tag, + size_t expectedSize) const + { + GetVectorValue(vector, tag); + + if (vector.size() != expectedSize) + { + LOG(ERROR) << "A vector in a DICOM tag has a bad size"; + throw Orthanc::OrthancException(Orthanc::ErrorCode_BadFileFormat); + } + } + + + void DicomDataset::Print() const + { + for (Values::const_iterator it = values_.begin(); it != values_.end(); ++it) + { + printf("%04x,%04x = [%s]\n", it->first.first, it->first.second, it->second.c_str()); + } + printf("\n"); + } + + + bool DicomDataset::IsGrayscale() const + { + std::string photometric = Orthanc::Toolbox::StripSpaces(GetStringValue(DICOM_TAG_PHOTOMETRIC_INTERPRETATION)); + + return (photometric == "MONOCHROME1" || + photometric == "MONOCHROME2"); + } + + + void DicomDataset::GetPixelSpacing(double& spacingX, + double& spacingY) const + { + if (HasTag(DICOM_TAG_PIXEL_SPACING)) + { + Vector spacing; + GetVectorValue(spacing, DICOM_TAG_PIXEL_SPACING, 2); + spacingX = spacing[0]; + spacingY = spacing[1]; + } + else + { + spacingX = 1.0; + spacingY = 1.0; + } + } +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/Resources/Graveyard/Toolbox/DicomDataset.h Wed Dec 21 14:19:38 2016 +0100 @@ -0,0 +1,121 @@ +/** + * Stone of Orthanc + * Copyright (C) 2012-2016 Sebastien Jodogne, Medical Physics + * Department, University Hospital of Liege, Belgium + * + * This program is free software: you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation, either version 3 of the + * License, or (at your option) any later version. + * + * In addition, as a special exception, the copyright holders of this + * program give permission to link the code of its release with the + * OpenSSL project's "OpenSSL" library (or with modified versions of it + * that use the same license as the "OpenSSL" library), and distribute + * the linked executables. You must obey the GNU General Public License + * in all respects for all of the code used other than "OpenSSL". If you + * modify file(s) with this exception, you may extend this exception to + * your version of the file(s), but you are not obligated to do so. If + * you do not wish to do so, delete this exception statement from your + * version. If you delete this exception statement from all source files + * in the program, then also delete it here. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + **/ + + +#pragma once + +#include "GeometryToolbox.h" +#include "../../Resources/Orthanc/Plugins/Samples/Common/IOrthancConnection.h" + +#include <map> +#include <stdint.h> +#include <json/value.h> + +namespace OrthancStone +{ + // This class is NOT thread-safe + // This is a lightweight alternative to Orthanc::DicomMap + class DicomDataset : public boost::noncopyable + { + public: + typedef std::pair<uint16_t, uint16_t> Tag; + + private: + typedef std::map<Tag, std::string> Values; + + Values values_; + + void Parse(const std::string& content); + + void Parse(const Json::Value& content); + + public: + DicomDataset(const std::string& content) + { + Parse(content); + } + + DicomDataset(const Json::Value& content) + { + Parse(content); + } + + DicomDataset(OrthancPlugins::IOrthancConnection& orthanc, + const std::string& instanceId); + + bool HasTag(const Tag& tag) const + { + return values_.find(tag) != values_.end(); + } + + std::string GetStringValue(const Tag& tag) const; + + std::string GetStringValue(const Tag& tag, + const std::string& defaultValue) const; + + float GetFloatValue(const Tag& tag) const; + + double GetDoubleValue(const Tag& tag) const; + + int GetIntegerValue(const Tag& tag) const; + + unsigned int GetUnsignedIntegerValue(const Tag& tag) const; + + void GetVectorValue(Vector& vector, + const Tag& tag, + size_t expectedSize) const; + + void GetVectorValue(Vector& vector, + const Tag& tag) const; + + void Print() const; + + bool IsGrayscale() const; + + void GetPixelSpacing(double& spacingX, + double& spacingY) const; + }; + + + static const DicomDataset::Tag DICOM_TAG_COLUMNS(0x0028, 0x0011); + static const DicomDataset::Tag DICOM_TAG_IMAGE_ORIENTATION_PATIENT(0x0020, 0x0037); + static const DicomDataset::Tag DICOM_TAG_IMAGE_POSITION_PATIENT(0x0020, 0x0032); + static const DicomDataset::Tag DICOM_TAG_NUMBER_OF_FRAMES(0x0028, 0x0008); + static const DicomDataset::Tag DICOM_TAG_PIXEL_REPRESENTATION(0x0028, 0x0103); + static const DicomDataset::Tag DICOM_TAG_PIXEL_SPACING(0x0028, 0x0030); + static const DicomDataset::Tag DICOM_TAG_RESCALE_INTERCEPT(0x0028, 0x1052); + static const DicomDataset::Tag DICOM_TAG_RESCALE_SLOPE(0x0028, 0x1053); + static const DicomDataset::Tag DICOM_TAG_ROWS(0x0028, 0x0010); + static const DicomDataset::Tag DICOM_TAG_SLICE_THICKNESS(0x0018, 0x0050); + static const DicomDataset::Tag DICOM_TAG_WINDOW_CENTER(0x0028, 0x1050); + static const DicomDataset::Tag DICOM_TAG_WINDOW_WIDTH(0x0028, 0x1051); + static const DicomDataset::Tag DICOM_TAG_PHOTOMETRIC_INTERPRETATION(0x0028, 0x0004); +}
--- a/Resources/Orthanc/Core/SystemToolbox.cpp Mon Dec 19 12:55:14 2016 +0100 +++ b/Resources/Orthanc/Core/SystemToolbox.cpp Wed Dec 21 14:19:38 2016 +0100 @@ -123,7 +123,7 @@ barrierEvent_ = ServerBarrierEvent_Stop; while (!(*stopFlag || finish_)) { - Toolbox::USleep(100 * 1000); + SystemToolbox::USleep(100 * 1000); } #if defined(_WIN32) @@ -152,6 +152,18 @@ } + void SystemToolbox::USleep(uint64_t microSeconds) + { +#if defined(_WIN32) + ::Sleep(static_cast<DWORD>(microSeconds / static_cast<uint64_t>(1000))); +#elif defined(__linux__) || defined(__APPLE__) || defined(__FreeBSD_kernel__) || defined(__FreeBSD__) || defined(__native_client__) + usleep(microSeconds); +#else +#error Support your platform here +#endif + } + + static std::streamsize GetStreamSize(std::istream& f) { // http://www.cplusplus.com/reference/iostream/istream/tellg/
--- a/Resources/Orthanc/Core/SystemToolbox.h Mon Dec 19 12:55:14 2016 +0100 +++ b/Resources/Orthanc/Core/SystemToolbox.h Wed Dec 21 14:19:38 2016 +0100 @@ -50,6 +50,8 @@ { namespace SystemToolbox { + void USleep(uint64_t microSeconds); + ServerBarrierEvent ServerBarrier(const bool& stopFlag); ServerBarrierEvent ServerBarrier();
--- a/Resources/Orthanc/Core/Toolbox.cpp Mon Dec 19 12:55:14 2016 +0100 +++ b/Resources/Orthanc/Core/Toolbox.cpp Wed Dec 21 14:19:38 2016 +0100 @@ -90,18 +90,6 @@ namespace Orthanc { - void Toolbox::USleep(uint64_t microSeconds) - { -#if defined(_WIN32) - ::Sleep(static_cast<DWORD>(microSeconds / static_cast<uint64_t>(1000))); -#elif defined(__linux__) || defined(__APPLE__) || defined(__FreeBSD_kernel__) || defined(__FreeBSD__) || defined(__native_client__) - usleep(microSeconds); -#else -#error Support your platform here -#endif - } - - void Toolbox::ToUpperCase(std::string& s) { std::transform(s.begin(), s.end(), s.begin(), toupper);
--- a/Resources/Orthanc/Core/Toolbox.h Mon Dec 19 12:55:14 2016 +0100 +++ b/Resources/Orthanc/Core/Toolbox.h Wed Dec 21 14:19:38 2016 +0100 @@ -78,8 +78,6 @@ namespace Toolbox { - void USleep(uint64_t microSeconds); - void ToUpperCase(std::string& s); // Inplace version void ToLowerCase(std::string& s); // Inplace version
--- a/Resources/Orthanc/Core/WebServiceParameters.cpp Mon Dec 19 12:55:14 2016 +0100 +++ b/Resources/Orthanc/Core/WebServiceParameters.cpp Wed Dec 21 14:19:38 2016 +0100 @@ -34,7 +34,6 @@ #include "WebServiceParameters.h" #include "../Core/Logging.h" -#include "../Core/Toolbox.h" #include "../Core/OrthancException.h" #if ORTHANC_SANDBOXED == 0
--- a/Resources/Orthanc/Plugins/Samples/Common/DicomPath.cpp Mon Dec 19 12:55:14 2016 +0100 +++ b/Resources/Orthanc/Plugins/Samples/Common/DicomPath.cpp Wed Dec 21 14:19:38 2016 +0100 @@ -49,20 +49,20 @@ } - DicomPath::DicomPath(DicomTag sequence, + DicomPath::DicomPath(const DicomTag& sequence, size_t index, - DicomTag tag) : + const DicomTag& tag) : finalTag_(tag) { AddToPrefix(sequence, index); } - DicomPath::DicomPath(DicomTag sequence1, + DicomPath::DicomPath(const DicomTag& sequence1, size_t index1, - DicomTag sequence2, + const DicomTag& sequence2, size_t index2, - DicomTag tag) : + const DicomTag& tag) : finalTag_(tag) { AddToPrefix(sequence1, index1); @@ -70,13 +70,13 @@ } - DicomPath::DicomPath(DicomTag sequence1, + DicomPath::DicomPath(const DicomTag& sequence1, size_t index1, - DicomTag sequence2, + const DicomTag& sequence2, size_t index2, - DicomTag sequence3, + const DicomTag& sequence3, size_t index3, - DicomTag tag) : + const DicomTag& tag) : finalTag_(tag) { AddToPrefix(sequence1, index1);
--- a/Resources/Orthanc/Plugins/Samples/Common/DicomPath.h Mon Dec 19 12:55:14 2016 +0100 +++ b/Resources/Orthanc/Plugins/Samples/Common/DicomPath.h Wed Dec 21 14:19:38 2016 +0100 @@ -50,30 +50,30 @@ const Prefix& GetPrefixItem(size_t depth) const; public: - DicomPath(DicomTag finalTag) : + DicomPath(const DicomTag& finalTag) : finalTag_(finalTag) { } - DicomPath(DicomTag sequence, + DicomPath(const DicomTag& sequence, size_t index, - DicomTag tag); + const DicomTag& tag); - DicomPath(DicomTag sequence1, + DicomPath(const DicomTag& sequence1, size_t index1, - DicomTag sequence2, + const DicomTag& sequence2, size_t index2, - DicomTag tag); + const DicomTag& tag); - DicomPath(DicomTag sequence1, + DicomPath(const DicomTag& sequence1, size_t index1, - DicomTag sequence2, + const DicomTag& sequence2, size_t index2, - DicomTag sequence3, + const DicomTag& sequence3, size_t index3, - DicomTag tag); + const DicomTag& tag); - void AddToPrefix(DicomTag tag, + void AddToPrefix(const DicomTag& tag, size_t position) { prefix_.push_back(std::make_pair(tag, position));
--- a/Resources/Orthanc/Resources/CMake/BoostConfiguration.cmake Mon Dec 19 12:55:14 2016 +0100 +++ b/Resources/Orthanc/Resources/CMake/BoostConfiguration.cmake Wed Dec 21 14:19:38 2016 +0100 @@ -99,6 +99,13 @@ -DBOOST_LOCALE_NO_POSIX_BACKEND=1 -DBOOST_LOCALE_NO_STD_BACKEND=1 ) + + elseif (${CMAKE_SYSTEM_NAME} STREQUAL "Emscripten") + add_definitions( + -DBOOST_LOCALE_NO_POSIX_BACKEND=1 + -DBOOST_LOCALE_NO_STD_BACKEND=1 + ) + else() message(FATAL_ERROR "Support your platform here") endif() @@ -114,10 +121,15 @@ list(APPEND BOOST_SOURCES ${BOOST_REGEX_SOURCES} ${BOOST_SOURCES_DIR}/libs/date_time/src/gregorian/greg_month.cpp - ${BOOST_SOURCES_DIR}/libs/locale/src/encoding/codepage.cpp ${BOOST_SOURCES_DIR}/libs/system/src/error_code.cpp ) + if (NOT ${CMAKE_SYSTEM_NAME} STREQUAL "Emscripten") + list(APPEND BOOST_SOURCES + ${BOOST_SOURCES_DIR}/libs/locale/src/encoding/codepage.cpp + ) + endif() + if (${CMAKE_SYSTEM_NAME} STREQUAL "PNaCl" OR ${CMAKE_SYSTEM_NAME} STREQUAL "NaCl32" OR ${CMAKE_SYSTEM_NAME} STREQUAL "NaCl64")