1 /* 2 * Copyright (c) 2014, 2018, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 #ifndef PLATFORM_H 27 #define PLATFORM_H 28 29 #include "OrderedMap.h" 30 31 #include <stdio.h> 32 #include <stdlib.h> 33 #include <memory.h> 34 #include <string> 35 #include <map> 36 #include <list> 37 #include <vector> 38 39 40 #ifdef WIN32 41 #ifndef WINDOWS 42 #define WINDOWS 43 #endif 44 #endif //WIN32 45 46 #ifdef __APPLE__ 47 #define MAC 48 #define POSIX 49 #endif //__APPLE__ 50 51 52 #ifdef __linux 53 #ifndef LINUX 54 #define LINUX 55 #endif 56 #endif //__linux 57 58 #ifdef LINUX 59 #define POSIX 60 #endif //LINUX 61 62 63 64 #ifdef WINDOWS 65 // Define Windows compatibility requirements XP or later 66 #define WINVER 0x0600 67 #define _WIN32_WINNT 0x0600 68 69 #include <Windows.h> 70 #include <tchar.h> 71 #include <shlobj.h> 72 #include <direct.h> 73 #include <process.h> 74 #include <malloc.h> 75 76 typedef std::wstring TString; 77 #define StringLength wcslen 78 79 #define TRAILING_PATHSEPARATOR '\\' 80 #define BAD_TRAILING_PATHSEPARATOR '/' 81 #define PATH_SEPARATOR ';' 82 #define BAD_PATH_SEPARATOR ':' 83 84 typedef ULONGLONG TPlatformNumber; 85 typedef DWORD TProcessID; 86 87 #endif //WINDOWS 88 89 90 #ifdef POSIX 91 #include <errno.h> 92 #include <unistd.h> 93 #include <sys/stat.h> 94 #include <dlfcn.h> 95 #include <libgen.h> 96 97 #define _T(x) x 98 99 typedef char TCHAR; 100 typedef std::string TString; 101 #define StringLength strlen 102 103 typedef unsigned long DWORD; 104 105 #define TRAILING_PATHSEPARATOR '/' 106 #define BAD_TRAILING_PATHSEPARATOR '\\' 107 #define PATH_SEPARATOR ':' 108 #define BAD_PATH_SEPARATOR ';' 109 #define MAX_PATH 1000 110 111 typedef long TPlatformNumber; 112 typedef pid_t TProcessID; 113 114 #define HMODULE void* 115 #endif //POSIX 116 117 118 // Config file sections 119 #define CONFIG_SECTION_APPLICATION _T("CONFIG_SECTION_APPLICATION") 120 #define CONFIG_SECTION_JVMOPTIONS _T("CONFIG_SECTION_JVMOPTIONS") 121 #define CONFIG_SECTION_APPCDSJVMOPTIONS _T("CONFIG_SECTION_APPCDSJVMOPTIONS") 122 #define CONFIG_SECTION_ARGOPTIONS _T("CONFIG_SECTION_ARGOPTIONS") 123 #define CONFIG_SECTION_APPCDSGENERATECACHEJVMOPTIONS \ 124 _T("CONFIG_SECTION_APPCDSGENERATECACHEJVMOPTIONS") 125 126 // Config file keys. 127 #define CONFIG_VERSION _T("CONFIG_VERSION") 128 #define CONFIG_MAINJAR_KEY _T("CONFIG_MAINJAR_KEY") 129 #define CONFIG_MAINMODULE_KEY _T("CONFIG_MAINMODULE_KEY") 130 #define CONFIG_MAINCLASSNAME_KEY _T("CONFIG_MAINCLASSNAME_KEY") 131 #define CONFIG_CLASSPATH_KEY _T("CONFIG_CLASSPATH_KEY") 132 #define CONFIG_MODULEPATH_KEY _T("CONFIG_MODULEPATH_KEY") 133 #define APP_NAME_KEY _T("APP_NAME_KEY") 134 #define CONFIG_SPLASH_KEY _T("CONFIG_SPLASH_KEY") 135 #define CONFIG_APP_ID_KEY _T("CONFIG_APP_ID_KEY") 136 #define CONFIG_APP_MEMORY _T("CONFIG_APP_MEMORY") 137 #define CONFIG_APP_DEBUG _T("CONFIG_APP_DEBUG") 138 #define CONFIG_APPLICATION_INSTANCE _T("CONFIG_APPLICATION_INSTANCE") 139 140 #define JVM_RUNTIME_KEY _T("JVM_RUNTIME_KEY") 141 #define JPACKAGER_APP_DATA_DIR _T("CONFIG_APP_IDENTIFIER") 142 143 144 145 typedef void* Module; 146 typedef void* Procedure; 147 148 149 template <typename ObjectType, typename ValueType, 150 ValueType (ObjectType::*getter)(void), 151 void (ObjectType::*setter)(ValueType)> 152 class Property { 153 private: 154 ObjectType* FObject; 155 156 public: 157 Property() { 158 FObject = NULL; 159 } 160 161 void SetInstance(ObjectType* Value) { 162 FObject = Value; 163 } 164 165 // To set the value using the set method. 166 ValueType operator =(const ValueType& Value) { 167 assert(FObject != NULL); 168 (FObject->*setter)(Value); 169 return Value; 170 } 171 172 // The Property class is treated as the internal type. 173 operator ValueType() { 174 assert(FObject != NULL); 175 return (FObject->*getter)(); 176 } 177 }; 178 179 template <typename ObjectType, typename ValueType, 180 ValueType (ObjectType::*getter)(void)> 181 class ReadProperty { 182 private: 183 ObjectType* FObject; 184 185 public: 186 ReadProperty() { 187 FObject = NULL; 188 } 189 190 void SetInstance(ObjectType* Value) { 191 FObject = Value; 192 } 193 194 // The Property class is treated as the internal type. 195 operator ValueType() { 196 assert(FObject != NULL); 197 return (FObject->*getter)(); 198 } 199 }; 200 201 template <typename ObjectType, typename ValueType, 202 void (ObjectType::*setter)(ValueType)> 203 class WriteProperty { 204 private: 205 ObjectType* FObject; 206 207 public: 208 WriteProperty() { 209 FObject = NULL; 210 } 211 212 void SetInstance(ObjectType* Value) { 213 FObject = Value; 214 } 215 216 // To set the value using the set method. 217 ValueType operator =(const ValueType& Value) { 218 assert(FObject != NULL); 219 (FObject->*setter)(Value); 220 return Value; 221 } 222 }; 223 224 template <typename ValueType, 225 ValueType (*getter)(void), void (*setter)(ValueType)> 226 class StaticProperty { 227 public: 228 StaticProperty() { 229 } 230 231 // To set the value using the set method. 232 ValueType operator =(const ValueType& Value) { 233 (*getter)(Value); 234 return Value; 235 } 236 237 // The Property class is treated as the internal type which is the getter. 238 operator ValueType() { 239 return (*setter)(); 240 } 241 }; 242 243 template <typename ValueType, ValueType (*getter)(void)> 244 class StaticReadProperty { 245 public: 246 StaticReadProperty() { 247 } 248 249 // The Property class is treated as the internal type which is the getter. 250 operator ValueType() { 251 return (*getter)(); 252 } 253 }; 254 255 template <typename ValueType, void (*setter)(ValueType)> 256 class StaticWriteProperty { 257 public: 258 StaticWriteProperty() { 259 } 260 261 // To set the value using the set method. 262 ValueType operator =(const ValueType& Value) { 263 (*setter)(Value); 264 return Value; 265 } 266 }; 267 268 269 class Process { 270 protected: 271 std::list<TString> FOutput; 272 273 public: 274 Process() { 275 Output.SetInstance(this); 276 Input.SetInstance(this); 277 } 278 279 virtual ~Process() {} 280 281 virtual bool IsRunning() = 0; 282 virtual bool Terminate() = 0; 283 virtual bool Execute(const TString Application, 284 const std::vector<TString> Arguments, bool AWait = false) = 0; 285 virtual bool Wait() = 0; 286 virtual TProcessID GetProcessID() = 0; 287 288 virtual std::list<TString> GetOutput() { return FOutput; } 289 virtual void SetInput(TString Value) = 0; 290 291 ReadProperty<Process, std::list<TString>, &Process::GetOutput> Output; 292 WriteProperty<Process, TString, &Process::SetInput> Input; 293 }; 294 295 296 template <typename T> 297 class AutoFreePtr { 298 private: 299 T* FObject; 300 301 public: 302 AutoFreePtr() { 303 FObject = NULL; 304 } 305 306 AutoFreePtr(T* Value) { 307 FObject = Value; 308 } 309 310 ~AutoFreePtr() { 311 if (FObject != NULL) { 312 delete FObject; 313 } 314 } 315 316 operator T* () const { 317 return FObject; 318 } 319 320 T& operator* () const { 321 return *FObject; 322 } 323 324 T* operator->() const { 325 return FObject; 326 } 327 328 T** operator&() { 329 return &FObject; 330 } 331 332 T* operator=(const T * rhs) { 333 FObject = rhs; 334 return FObject; 335 } 336 }; 337 338 339 class IPropertyContainer { 340 public: 341 IPropertyContainer(void) {} 342 virtual ~IPropertyContainer(void) {} 343 344 virtual bool GetValue(const TString Key, TString& Value) = 0; 345 virtual size_t GetCount() = 0; 346 }; 347 348 class ISectionalPropertyContainer { 349 public: 350 ISectionalPropertyContainer(void) {} 351 virtual ~ISectionalPropertyContainer(void) {} 352 353 virtual bool GetValue(const TString SectionName, 354 const TString Key, TString& Value) = 0; 355 virtual bool ContainsSection(const TString SectionName) = 0; 356 virtual bool GetSection(const TString SectionName, 357 OrderedMap<TString, TString> &Data) = 0; 358 }; 359 360 class Environment { 361 private: 362 Environment() { 363 } 364 365 public: 366 static TString GetNewLine() { 367 #ifdef WINDOWS 368 return _T("\r\n"); 369 #endif //WINDOWS 370 #ifdef POSIX 371 return _T("\n"); 372 #endif //POSIX 373 } 374 375 static StaticReadProperty<TString, &Environment::GetNewLine> NewLine; 376 }; 377 378 379 enum DebugState {dsNone, dsNative, dsJava}; 380 enum MessageResponse {mrOK, mrCancel}; 381 enum AppCDSState {cdsUninitialized, cdsDisabled, 382 cdsEnabled, cdsAuto, cdsGenCache}; 383 384 class Platform { 385 private: 386 AppCDSState FAppCDSState; 387 388 protected: 389 TProcessID singleInstanceProcessId; 390 391 Platform(void): FAppCDSState(cdsUninitialized), singleInstanceProcessId(0) { 392 } 393 394 public: 395 AppCDSState GetAppCDSState() { return FAppCDSState; } 396 void SetAppCDSState(AppCDSState Value) { FAppCDSState = Value; } 397 TProcessID GetSingleInstanceProcessId() { return singleInstanceProcessId; } 398 399 static Platform& GetInstance(); 400 401 virtual ~Platform(void) {} 402 403 public: 404 virtual void ShowMessage(TString title, TString description) = 0; 405 virtual void ShowMessage(TString description) = 0; 406 virtual MessageResponse ShowResponseMessage(TString title, 407 TString description) = 0; 408 409 virtual void SetCurrentDirectory(TString Value) = 0; 410 411 // Caller must free result using delete[]. 412 virtual TCHAR* ConvertStringToFileSystemString(TCHAR* Source, 413 bool &release) = 0; 414 415 // Caller must free result using delete[]. 416 virtual TCHAR* ConvertFileSystemStringToString(TCHAR* Source, 417 bool &release) = 0; 418 419 // Returns: 420 // Windows=C:\Users\<username>\AppData\Local 421 // Linux=~/.local 422 // Mac=~/Library/Application Support 423 virtual TString GetAppDataDirectory() = 0; 424 425 virtual TString GetPackageAppDirectory() = 0; 426 virtual TString GetPackageLauncherDirectory() = 0; 427 virtual TString GetPackageRuntimeBinDirectory() = 0; 428 virtual TString GetAppName() = 0; 429 430 virtual TString GetConfigFileName() = 0; 431 432 virtual TString GetBundledJVMLibraryFileName(TString RuntimePath) = 0; 433 434 // Caller must free result. 435 virtual ISectionalPropertyContainer* GetConfigFile(TString FileName) = 0; 436 437 virtual TString GetModuleFileName() = 0; 438 virtual TString GetPackageRootDirectory() = 0; 439 440 virtual Module LoadLibrary(TString FileName) = 0; 441 virtual void FreeLibrary(Module Module) = 0; 442 virtual Procedure GetProcAddress(Module Module, std::string MethodName) = 0; 443 virtual std::vector<TString> GetLibraryImports(const TString FileName) = 0; 444 virtual std::vector<TString> FilterOutRuntimeDependenciesForPlatform( 445 std::vector<TString> Imports) = 0; 446 447 // Caller must free result. 448 virtual Process* CreateProcess() = 0; 449 450 virtual bool IsMainThread() = 0; 451 virtual bool CheckForSingleInstance(TString Name) = 0; 452 virtual void reactivateAnotherInstance() = 0; 453 454 // Returns megabytes. 455 virtual TPlatformNumber GetMemorySize() = 0; 456 457 virtual std::map<TString, TString> GetKeys() = 0; 458 459 virtual std::list<TString> LoadFromFile(TString FileName) = 0; 460 virtual void SaveToFile(TString FileName, 461 std::list<TString> Contents, bool ownerOnly) = 0; 462 463 virtual TString GetTempDirectory() = 0; 464 465 #ifdef DEBUG 466 virtual DebugState GetDebugState() = 0; 467 virtual int GetProcessID() = 0; 468 virtual bool IsNativeDebuggerPresent() = 0; 469 #endif //DEBUG 470 }; 471 472 473 class Library { 474 private: 475 std::vector<TString> *FDependentLibraryNames; 476 std::vector<Library*> *FDependenciesLibraries; 477 Module FModule; 478 std::string fname; 479 480 void Initialize(); 481 void InitializeDependencies(); 482 void LoadDependencies(); 483 void UnloadDependencies(); 484 485 public: 486 void* GetProcAddress(const std::string& MethodName) const; 487 488 public: 489 Library(); 490 Library(const TString &FileName); 491 ~Library(); 492 493 bool Load(const TString &FileName); 494 bool Unload(); 495 496 const std::string& GetName() const { 497 return fname; 498 } 499 500 void AddDependency(const TString &FileName); 501 void AddDependencies(const std::vector<TString> &Dependencies); 502 }; 503 504 505 class Exception: public std::exception { 506 private: 507 TString FMessage; 508 509 protected: 510 void SetMessage(const TString Message) { 511 FMessage = Message; 512 } 513 514 public: 515 explicit Exception() : exception() {} 516 explicit Exception(const TString Message) : exception() { 517 SetMessage(Message); 518 } 519 virtual ~Exception() throw() {} 520 521 TString GetMessage() { return FMessage; } 522 }; 523 524 class FileNotFoundException: public Exception { 525 public: 526 explicit FileNotFoundException(const TString Message) : Exception(Message) {} 527 }; 528 529 #endif // PLATFORM_H