1 /* 2 * Copyright (c) 2014, 2015, 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_MAINCLASSNAME_KEY _T("CONFIG_MAINCLASSNAME_KEY") 139 #define CONFIG_CLASSPATH_KEY _T("CONFIG_CLASSPATH_KEY") 140 #define CONFIG_MODULEPATH_KEY _T("CONFIG_MODULEPATH_KEY") 141 #define APP_NAME_KEY _T("APP_NAME_KEY") 142 #define CONFIG_SPLASH_KEY _T("CONFIG_SPLASH_KEY") 143 #define CONFIG_APP_ID_KEY _T("CONFIG_APP_ID_KEY") 144 #define CONFIG_APP_MEMORY _T("CONFIG_APP_MEMORY") 145 146 #define JVM_RUNTIME_KEY _T("JVM_RUNTIME_KEY") 147 #define PACKAGER_APP_DATA_DIR _T("CONFIG_APP_IDENTIFIER") 148 149 150 151 typedef void* Module; 152 typedef void* Procedure; 153 154 155 template <typename ObjectType, typename ValueType, ValueType (ObjectType::*getter)(void), void (ObjectType::*setter)(ValueType)> 156 class Property { 157 private: 158 ObjectType* FObject; 159 160 public: 161 Property() { 162 FObject = NULL; 163 } 164 165 void SetInstance(ObjectType* Value) { 166 FObject = Value; 167 } 168 169 // To set the value using the set method. 170 ValueType operator =(const ValueType& Value) { 171 assert(FObject != NULL); 172 (FObject->*setter)(Value); 173 return Value; 174 } 175 176 // The Property class is treated as the internal type. 177 operator ValueType() { 178 assert(FObject != NULL); 179 return (FObject->*getter)(); 180 } 181 }; 182 183 template <typename ObjectType, typename ValueType, ValueType (ObjectType::*getter)(void)> 184 class ReadProperty { 185 private: 186 ObjectType* FObject; 187 188 public: 189 ReadProperty() { 190 FObject = NULL; 191 } 192 193 void SetInstance(ObjectType* Value) { 194 FObject = Value; 195 } 196 197 // The Property class is treated as the internal type. 198 operator ValueType() { 199 assert(FObject != NULL); 200 return (FObject->*getter)(); 201 } 202 }; 203 204 template <typename ObjectType, typename ValueType, void (ObjectType::*setter)(ValueType)> 205 class WriteProperty { 206 private: 207 ObjectType* FObject; 208 209 public: 210 WriteProperty() { 211 FObject = NULL; 212 } 213 214 void SetInstance(ObjectType* Value) { 215 FObject = Value; 216 } 217 218 // To set the value using the set method. 219 ValueType operator =(const ValueType& Value) { 220 assert(FObject != NULL); 221 (FObject->*setter)(Value); 222 return Value; 223 } 224 }; 225 226 template <typename ValueType, ValueType (*getter)(void), void (*setter)(ValueType)> 227 class StaticProperty { 228 public: 229 StaticProperty() { 230 } 231 232 // To set the value using the set method. 233 ValueType operator =(const ValueType& Value) { 234 (*getter)(Value); 235 return Value; 236 } 237 238 // The Property class is treated as the internal type which is the getter. 239 operator ValueType() { 240 return (*setter)(); 241 } 242 }; 243 244 template <typename ValueType, ValueType (*getter)(void)> 245 class StaticReadProperty { 246 public: 247 StaticReadProperty() { 248 } 249 250 // The Property class is treated as the internal type which is the getter. 251 operator ValueType() { 252 return (*getter)(); 253 } 254 }; 255 256 template <typename ValueType, void (*setter)(ValueType)> 257 class StaticWriteProperty { 258 public: 259 StaticWriteProperty() { 260 } 261 262 // To set the value using the set method. 263 ValueType operator =(const ValueType& Value) { 264 (*setter)(Value); 265 return Value; 266 } 267 }; 268 269 270 class Process { 271 protected: 272 std::list<TString> FOutput; 273 274 public: 275 Process() { 276 Output.SetInstance(this); 277 Input.SetInstance(this); 278 } 279 280 virtual ~Process() {} 281 282 virtual bool IsRunning() = 0; 283 virtual bool Terminate() = 0; 284 virtual bool Execute(const TString Application, const std::vector<TString> Arguments, 285 bool AWait = false) = 0; 286 virtual bool Wait() = 0; 287 virtual TProcessID GetProcessID() = 0; 288 289 virtual std::list<TString> GetOutput() { return FOutput; } 290 virtual void SetInput(TString Value) = 0; 291 292 ReadProperty<Process, std::list<TString>, &Process::GetOutput> Output; 293 WriteProperty<Process, TString, &Process::SetInput> Input; 294 }; 295 296 297 template <typename T> 298 class AutoFreePtr { 299 private: 300 T* FObject; 301 302 public: 303 AutoFreePtr() { 304 FObject = NULL; 305 } 306 307 AutoFreePtr(T* Value) { 308 FObject = Value; 309 } 310 311 ~AutoFreePtr() { 312 if (FObject != NULL) { 313 delete FObject; 314 } 315 } 316 317 operator T* () const { 318 return FObject; 319 } 320 321 T& operator* () const { 322 return *FObject; 323 } 324 325 T* operator->() const { 326 return FObject; 327 } 328 329 T** operator&() { 330 return &FObject; 331 } 332 333 T* operator=(const T * rhs) { 334 FObject = rhs; 335 return FObject; 336 } 337 }; 338 339 340 class IPropertyContainer { 341 public: 342 IPropertyContainer(void) {} 343 virtual ~IPropertyContainer(void) {} 344 345 virtual bool GetValue(const TString Key, TString& Value) = 0; 346 virtual size_t GetCount() = 0; 347 }; 348 349 class ISectionalPropertyContainer { 350 public: 351 ISectionalPropertyContainer(void) {} 352 virtual ~ISectionalPropertyContainer(void) {} 353 354 virtual bool GetValue(const TString SectionName, const TString Key, TString& Value) = 0; 355 virtual bool ContainsSection(const TString SectionName) = 0; 356 virtual bool GetSection(const TString SectionName, OrderedMap<TString, TString> &Data) = 0; 357 }; 358 359 class Environment { 360 private: 361 Environment() { 362 } 363 364 public: 365 static TString GetNewLine() { 366 #ifdef WINDOWS 367 return _T("\r\n"); 368 #endif //WINDOWS 369 #ifdef POSIX 370 return _T("\n"); 371 #endif //POSIX 372 } 373 374 static StaticReadProperty<TString, &Environment::GetNewLine> NewLine; 375 }; 376 377 378 enum DebugState {dsNone, dsNative, dsJava}; 379 enum MessageResponse {mrOK, mrCancel}; 380 enum AppCDSState {cdsUninitialized, cdsDisabled, cdsEnabled, cdsAuto, cdsGenCache}; 381 382 class Platform { 383 private: 384 AppCDSState FAppCDSState; 385 386 protected: 387 Platform(void) { 388 FAppCDSState = cdsUninitialized; 389 } 390 391 public: 392 AppCDSState GetAppCDSState() { return FAppCDSState; } 393 void SetAppCDSState(AppCDSState Value) { FAppCDSState = Value; } 394 395 static Platform& GetInstance(); 396 397 virtual ~Platform(void) {} 398 399 public: 400 virtual void ShowMessage(TString title, TString description) = 0; 401 virtual void ShowMessage(TString description) = 0; 402 virtual MessageResponse ShowResponseMessage(TString title, TString description) = 0; 403 // virtual MessageResponse ShowResponseMessage(TString description) = 0; 404 405 virtual void SetCurrentDirectory(TString Value) = 0; 406 407 // Caller must free result using delete[]. 408 virtual TCHAR* ConvertStringToFileSystemString(TCHAR* Source, bool &release) = 0; 409 410 // Caller must free result using delete[]. 411 virtual TCHAR* ConvertFileSystemStringToString(TCHAR* Source, bool &release) = 0; 412 413 // Returns: 414 // Windows=C:\Users\<username>\AppData\Local\<app.identifier>\packager\jvmuserargs.cfg 415 // Linux=~/.local/<app.identifier>/packager/jvmuserargs.cfg 416 // Mac=~/Library/Application Support/<app.identifier>/packager/jvmuserargs.cfg 417 virtual TString GetAppDataDirectory() = 0; 418 419 virtual TString GetPackageAppDirectory() = 0; 420 virtual TString GetPackageLauncherDirectory() = 0; 421 virtual TString GetAppName() = 0; 422 423 virtual TString GetConfigFileName() = 0; 424 425 virtual TString GetBundledJVMLibraryFileName(TString RuntimePath) = 0; 426 virtual TString GetSystemJVMLibraryFileName() = 0; 427 virtual TString GetSystemJRE() = 0; 428 429 // Caller must free result. 430 virtual ISectionalPropertyContainer* GetConfigFile(TString FileName) = 0; 431 432 virtual TString GetModuleFileName() = 0; 433 virtual TString GetPackageRootDirectory() = 0; 434 435 virtual Module LoadLibrary(TString FileName) = 0; 436 virtual void FreeLibrary(Module Module) = 0; 437 virtual Procedure GetProcAddress(Module Module, std::string MethodName) = 0; 438 virtual std::vector<TString> GetLibraryImports(const TString FileName) = 0; 439 virtual std::vector<TString> FilterOutRuntimeDependenciesForPlatform(std::vector<TString> Imports) = 0; 440 441 // Caller must free result. 442 virtual Process* CreateProcess() = 0; 443 444 virtual bool IsMainThread() = 0; 445 446 // Returns megabytes. 447 virtual TPlatformNumber GetMemorySize() = 0; 448 449 virtual std::map<TString, TString> GetKeys() = 0; 450 451 virtual std::list<TString> LoadFromFile(TString FileName) = 0; 452 virtual void SaveToFile(TString FileName, std::list<TString> Contents, bool ownerOnly) = 0; 453 454 #ifdef DEBUG 455 virtual DebugState GetDebugState() = 0; 456 virtual int GetProcessID() = 0; 457 virtual bool IsNativeDebuggerPresent() = 0; 458 #endif //DEBUG 459 }; 460 461 462 class Library { 463 private: 464 std::vector<TString> *FDependentLibraryNames; 465 std::vector<Library*> *FDependenciesLibraries; 466 Module FModule; 467 468 void Initialize(); 469 void InitializeDependencies(); 470 void LoadDependencies(); 471 void UnloadDependencies(); 472 473 protected: 474 void* GetProcAddress(std::string MethodName); 475 476 public: 477 Library(); 478 Library(const TString &FileName); 479 ~Library(); 480 481 bool Load(const TString &FileName); 482 bool Unload(); 483 484 void AddDependency(const TString &FileName); 485 void AddDependencies(const std::vector<TString> &Dependencies); 486 }; 487 488 489 class Exception: public std::exception { 490 private: 491 TString FMessage; 492 493 protected: 494 void SetMessage(const TString Message) { 495 FMessage = Message; 496 } 497 498 public: 499 explicit Exception() : exception() {} 500 explicit Exception(const TString Message) : exception() { 501 SetMessage(Message); 502 } 503 virtual ~Exception() throw() {} 504 505 TString GetMessage() { return FMessage; } 506 }; 507 508 class FileNotFoundException: public Exception { 509 public: 510 explicit FileNotFoundException(const TString Message) : Exception(Message) {} 511 }; 512 513 #endif //PLATFORM_H