1 /* 2 * Copyright (c) 2014, 2016, Oracle and/or its affiliates. 3 * All rights reserved. Use is subject to license terms. 4 * 5 * This file is available and licensed under the following license: 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 11 * - Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * - Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in 15 * the documentation and/or other materials provided with the distribution. 16 * - Neither the name of Oracle Corporation nor the names of its 17 * contributors may be used to endorse or promote products derived 18 * from this software without specific prior written permission. 19 * 20 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 21 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 22 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 23 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 24 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 25 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 26 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 27 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 28 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 29 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 30 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 31 */ 32 33 34 #ifndef PLATFORM_H 35 #define PLATFORM_H 36 37 #include "OrderedMap.h" 38 39 #include <stdio.h> 40 #include <stdlib.h> 41 #include <memory.h> 42 #include <string> 43 #include <map> 44 #include <list> 45 #include <vector> 46 47 48 #ifdef WIN32 49 #define WINDOWS 50 #endif //WIN32 51 52 #ifdef __APPLE__ 53 #define MAC 54 #define POSIX 55 #endif //__APPLE__ 56 57 58 #ifdef __linux 59 #define LINUX 60 #endif //__linux 61 62 #ifdef LINUX 63 #define POSIX 64 #endif //LINUX 65 66 67 68 #ifdef WINDOWS 69 // Define Windows compatibility requirements XP or later 70 #define WINVER 0x0501 71 #define _WIN32_WINNT 0x0501 72 73 #include <Windows.h> 74 #include <tchar.h> 75 #include <shlobj.h> 76 #include <direct.h> 77 #include <process.h> 78 #include <malloc.h> 79 80 typedef std::wstring TString; 81 #define StringLength wcslen 82 83 #define TRAILING_PATHSEPARATOR '\\' 84 #define BAD_TRAILING_PATHSEPARATOR '/' 85 #define PATH_SEPARATOR ';' 86 #define BAD_PATH_SEPARATOR ':' 87 88 typedef ULONGLONG TPlatformNumber; 89 typedef DWORD TProcessID; 90 91 #if defined _DEBUG && !defined DEBUG 92 #define DEBUG 93 #endif 94 95 #endif //WINDOWS 96 97 98 #ifdef POSIX 99 #include <errno.h> 100 #include <unistd.h> 101 #include <sys/stat.h> 102 #include <dlfcn.h> 103 #include <libgen.h> 104 105 #define _T(x) x 106 107 typedef char TCHAR; 108 typedef std::string TString; 109 #define StringLength strlen 110 111 typedef unsigned long DWORD; 112 113 #define TRAILING_PATHSEPARATOR '/' 114 #define BAD_TRAILING_PATHSEPARATOR '\\' 115 #define PATH_SEPARATOR ':' 116 #define BAD_PATH_SEPARATOR ';' 117 #define MAX_PATH 1000 118 119 typedef long TPlatformNumber; 120 typedef pid_t TProcessID; 121 122 #define HMODULE void* 123 #endif //POSIX 124 125 126 // Config file sections 127 #define CONFIG_SECTION_APPLICATION _T("CONFIG_SECTION_APPLICATION") 128 #define CONFIG_SECTION_JVMOPTIONS _T("CONFIG_SECTION_JVMOPTIONS") 129 #define CONFIG_SECTION_JVMUSEROPTIONS _T("CONFIG_SECTION_JVMUSEROPTIONS") 130 #define CONFIG_SECTION_JVMUSEROVERRIDESOPTIONS _T("CONFIG_SECTION_JVMUSEROVERRIDESOPTIONS") 131 #define CONFIG_SECTION_APPCDSJVMOPTIONS _T("CONFIG_SECTION_APPCDSJVMOPTIONS") 132 #define CONFIG_SECTION_APPCDSGENERATECACHEJVMOPTIONS _T("CONFIG_SECTION_APPCDSGENERATECACHEJVMOPTIONS") 133 #define CONFIG_SECTION_ARGOPTIONS _T("CONFIG_SECTION_ARGOPTIONS") 134 135 // Config file keys. 136 #define CONFIG_VERSION _T("CONFIG_VERSION") 137 #define CONFIG_MAINJAR_KEY _T("CONFIG_MAINJAR_KEY") 138 #define CONFIG_MAINMODULE_KEY _T("CONFIG_MAINMODULE_KEY") 139 #define CONFIG_MAINCLASSNAME_KEY _T("CONFIG_MAINCLASSNAME_KEY") 140 #define CONFIG_CLASSPATH_KEY _T("CONFIG_CLASSPATH_KEY") 141 #define CONFIG_MODULEPATH_KEY _T("CONFIG_MODULEPATH_KEY") 142 #define APP_NAME_KEY _T("APP_NAME_KEY") 143 #define CONFIG_SPLASH_KEY _T("CONFIG_SPLASH_KEY") 144 #define CONFIG_APP_ID_KEY _T("CONFIG_APP_ID_KEY") 145 #define CONFIG_APP_MEMORY _T("CONFIG_APP_MEMORY") 146 #define CONFIG_APP_DEBUG _T("CONFIG_APP_DEBUG") 147 148 #define JVM_RUNTIME_KEY _T("JVM_RUNTIME_KEY") 149 #define PACKAGER_APP_DATA_DIR _T("CONFIG_APP_IDENTIFIER") 150 151 152 153 typedef void* Module; 154 typedef void* Procedure; 155 156 157 template <typename ObjectType, typename ValueType, ValueType (ObjectType::*getter)(void), void (ObjectType::*setter)(ValueType)> 158 class Property { 159 private: 160 ObjectType* FObject; 161 162 public: 163 Property() { 164 FObject = NULL; 165 } 166 167 void SetInstance(ObjectType* Value) { 168 FObject = Value; 169 } 170 171 // To set the value using the set method. 172 ValueType operator =(const ValueType& Value) { 173 assert(FObject != NULL); 174 (FObject->*setter)(Value); 175 return Value; 176 } 177 178 // The Property class is treated as the internal type. 179 operator ValueType() { 180 assert(FObject != NULL); 181 return (FObject->*getter)(); 182 } 183 }; 184 185 template <typename ObjectType, typename ValueType, ValueType (ObjectType::*getter)(void)> 186 class ReadProperty { 187 private: 188 ObjectType* FObject; 189 190 public: 191 ReadProperty() { 192 FObject = NULL; 193 } 194 195 void SetInstance(ObjectType* Value) { 196 FObject = Value; 197 } 198 199 // The Property class is treated as the internal type. 200 operator ValueType() { 201 assert(FObject != NULL); 202 return (FObject->*getter)(); 203 } 204 }; 205 206 template <typename ObjectType, typename ValueType, void (ObjectType::*setter)(ValueType)> 207 class WriteProperty { 208 private: 209 ObjectType* FObject; 210 211 public: 212 WriteProperty() { 213 FObject = NULL; 214 } 215 216 void SetInstance(ObjectType* Value) { 217 FObject = Value; 218 } 219 220 // To set the value using the set method. 221 ValueType operator =(const ValueType& Value) { 222 assert(FObject != NULL); 223 (FObject->*setter)(Value); 224 return Value; 225 } 226 }; 227 228 template <typename ValueType, ValueType (*getter)(void), void (*setter)(ValueType)> 229 class StaticProperty { 230 public: 231 StaticProperty() { 232 } 233 234 // To set the value using the set method. 235 ValueType operator =(const ValueType& Value) { 236 (*getter)(Value); 237 return Value; 238 } 239 240 // The Property class is treated as the internal type which is the getter. 241 operator ValueType() { 242 return (*setter)(); 243 } 244 }; 245 246 template <typename ValueType, ValueType (*getter)(void)> 247 class StaticReadProperty { 248 public: 249 StaticReadProperty() { 250 } 251 252 // The Property class is treated as the internal type which is the getter. 253 operator ValueType() { 254 return (*getter)(); 255 } 256 }; 257 258 template <typename ValueType, void (*setter)(ValueType)> 259 class StaticWriteProperty { 260 public: 261 StaticWriteProperty() { 262 } 263 264 // To set the value using the set method. 265 ValueType operator =(const ValueType& Value) { 266 (*setter)(Value); 267 return Value; 268 } 269 }; 270 271 272 class Process { 273 protected: 274 std::list<TString> FOutput; 275 276 public: 277 Process() { 278 Output.SetInstance(this); 279 Input.SetInstance(this); 280 } 281 282 virtual ~Process() {} 283 284 virtual bool IsRunning() = 0; 285 virtual bool Terminate() = 0; 286 virtual bool Execute(const TString Application, const std::vector<TString> Arguments, 287 bool AWait = false) = 0; 288 virtual bool Wait() = 0; 289 virtual TProcessID GetProcessID() = 0; 290 291 virtual std::list<TString> GetOutput() { return FOutput; } 292 virtual void SetInput(TString Value) = 0; 293 294 ReadProperty<Process, std::list<TString>, &Process::GetOutput> Output; 295 WriteProperty<Process, TString, &Process::SetInput> Input; 296 }; 297 298 299 template <typename T> 300 class AutoFreePtr { 301 private: 302 T* FObject; 303 304 public: 305 AutoFreePtr() { 306 FObject = NULL; 307 } 308 309 AutoFreePtr(T* Value) { 310 FObject = Value; 311 } 312 313 ~AutoFreePtr() { 314 if (FObject != NULL) { 315 delete FObject; 316 } 317 } 318 319 operator T* () const { 320 return FObject; 321 } 322 323 T& operator* () const { 324 return *FObject; 325 } 326 327 T* operator->() const { 328 return FObject; 329 } 330 331 T** operator&() { 332 return &FObject; 333 } 334 335 T* operator=(const T * rhs) { 336 FObject = rhs; 337 return FObject; 338 } 339 }; 340 341 342 class IPropertyContainer { 343 public: 344 IPropertyContainer(void) {} 345 virtual ~IPropertyContainer(void) {} 346 347 virtual bool GetValue(const TString Key, TString& Value) = 0; 348 virtual size_t GetCount() = 0; 349 }; 350 351 class ISectionalPropertyContainer { 352 public: 353 ISectionalPropertyContainer(void) {} 354 virtual ~ISectionalPropertyContainer(void) {} 355 356 virtual bool GetValue(const TString SectionName, const TString Key, TString& Value) = 0; 357 virtual bool ContainsSection(const TString SectionName) = 0; 358 virtual bool GetSection(const TString SectionName, OrderedMap<TString, TString> &Data) = 0; 359 }; 360 361 class Environment { 362 private: 363 Environment() { 364 } 365 366 public: 367 static TString GetNewLine() { 368 #ifdef WINDOWS 369 return _T("\r\n"); 370 #endif //WINDOWS 371 #ifdef POSIX 372 return _T("\n"); 373 #endif //POSIX 374 } 375 376 static StaticReadProperty<TString, &Environment::GetNewLine> NewLine; 377 }; 378 379 380 enum DebugState {dsNone, dsNative, dsJava}; 381 enum MessageResponse {mrOK, mrCancel}; 382 enum AppCDSState {cdsUninitialized, cdsDisabled, cdsEnabled, cdsAuto, cdsGenCache}; 383 384 class Platform { 385 private: 386 AppCDSState FAppCDSState; 387 388 protected: 389 Platform(void) { 390 FAppCDSState = cdsUninitialized; 391 } 392 393 public: 394 AppCDSState GetAppCDSState() { return FAppCDSState; } 395 void SetAppCDSState(AppCDSState Value) { FAppCDSState = Value; } 396 397 static Platform& GetInstance(); 398 399 virtual ~Platform(void) {} 400 401 public: 402 virtual void ShowMessage(TString title, TString description) = 0; 403 virtual void ShowMessage(TString description) = 0; 404 virtual MessageResponse ShowResponseMessage(TString title, TString description) = 0; 405 // virtual MessageResponse ShowResponseMessage(TString description) = 0; 406 407 virtual void SetCurrentDirectory(TString Value) = 0; 408 409 // Caller must free result using delete[]. 410 virtual TCHAR* ConvertStringToFileSystemString(TCHAR* Source, bool &release) = 0; 411 412 // Caller must free result using delete[]. 413 virtual TCHAR* ConvertFileSystemStringToString(TCHAR* Source, bool &release) = 0; 414 415 // Returns: 416 // Windows=C:\Users\<username>\AppData\Local\<app.identifier>\packager\jvmuserargs.cfg 417 // Linux=~/.local/<app.identifier>/packager/jvmuserargs.cfg 418 // Mac=~/Library/Application Support/<app.identifier>/packager/jvmuserargs.cfg 419 virtual TString GetAppDataDirectory() = 0; 420 421 virtual TString GetPackageAppDirectory() = 0; 422 virtual TString GetPackageLauncherDirectory() = 0; 423 virtual TString GetAppName() = 0; 424 425 virtual TString GetConfigFileName() = 0; 426 427 virtual TString GetBundledJVMLibraryFileName(TString RuntimePath) = 0; 428 virtual TString GetSystemJVMLibraryFileName() = 0; 429 virtual TString GetSystemJRE() = 0; 430 431 // Caller must free result. 432 virtual ISectionalPropertyContainer* GetConfigFile(TString FileName) = 0; 433 434 virtual TString GetModuleFileName() = 0; 435 virtual TString GetPackageRootDirectory() = 0; 436 437 virtual Module LoadLibrary(TString FileName) = 0; 438 virtual void FreeLibrary(Module Module) = 0; 439 virtual Procedure GetProcAddress(Module Module, std::string MethodName) = 0; 440 virtual std::vector<TString> GetLibraryImports(const TString FileName) = 0; 441 virtual std::vector<TString> FilterOutRuntimeDependenciesForPlatform(std::vector<TString> Imports) = 0; 442 443 // Caller must free result. 444 virtual Process* CreateProcess() = 0; 445 446 virtual bool IsMainThread() = 0; 447 448 // Returns megabytes. 449 virtual TPlatformNumber GetMemorySize() = 0; 450 451 virtual std::map<TString, TString> GetKeys() = 0; 452 453 virtual std::list<TString> LoadFromFile(TString FileName) = 0; 454 virtual void SaveToFile(TString FileName, std::list<TString> Contents, bool ownerOnly) = 0; 455 456 #ifdef DEBUG 457 virtual DebugState GetDebugState() = 0; 458 virtual int GetProcessID() = 0; 459 virtual bool IsNativeDebuggerPresent() = 0; 460 #endif //DEBUG 461 }; 462 463 464 class Library { 465 private: 466 std::vector<TString> *FDependentLibraryNames; 467 std::vector<Library*> *FDependenciesLibraries; 468 Module FModule; 469 470 void Initialize(); 471 void InitializeDependencies(); 472 void LoadDependencies(); 473 void UnloadDependencies(); 474 475 protected: 476 void* GetProcAddress(std::string MethodName); 477 478 public: 479 Library(); 480 Library(const TString &FileName); 481 ~Library(); 482 483 bool Load(const TString &FileName); 484 bool Unload(); 485 486 void AddDependency(const TString &FileName); 487 void AddDependencies(const std::vector<TString> &Dependencies); 488 }; 489 490 491 class Exception: public std::exception { 492 private: 493 TString FMessage; 494 495 protected: 496 void SetMessage(const TString Message) { 497 FMessage = Message; 498 } 499 500 public: 501 explicit Exception() : exception() {} 502 explicit Exception(const TString Message) : exception() { 503 SetMessage(Message); 504 } 505 virtual ~Exception() throw() {} 506 507 TString GetMessage() { return FMessage; } 508 }; 509 510 class FileNotFoundException: public Exception { 511 public: 512 explicit FileNotFoundException(const TString Message) : Exception(Message) {} 513 }; 514 515 #endif //PLATFORM_H