105 if (nbytes == OS_ERR) {
106 if (PrintMiscellaneous && Verbose) {
107 warning("Could not write Perfdata save file: %s: %s\n",
108 destfile, strerror(errno));
109 }
110 break;
111 }
112
113 remaining -= (size_t)nbytes;
114 addr += nbytes;
115 }
116
117 int result = ::_close(fd);
118 if (PrintMiscellaneous && Verbose) {
119 if (result == OS_ERR) {
120 warning("Could not close %s: %s\n", destfile, strerror(errno));
121 }
122 }
123 }
124
125 FREE_C_HEAP_ARRAY(char, destfile, mtInternal);
126 }
127
128 // Shared Memory Implementation Details
129
130 // Note: the win32 shared memory implementation uses two objects to represent
131 // the shared memory: a windows kernel based file mapping object and a backing
132 // store file. On windows, the name space for shared memory is a kernel
133 // based name space that is disjoint from other win32 name spaces. Since Java
134 // is unaware of this name space, a parallel file system based name space is
135 // maintained, which provides a common file system based shared memory name
136 // space across the supported platforms and one that Java apps can deal with
137 // through simple file apis.
138 //
139 // For performance and resource cleanup reasons, it is recommended that the
140 // user specific directory and the backing store file be stored in either a
141 // RAM based file system or a local disk based file system. Network based
142 // file systems are not recommended for performance reasons. In addition,
143 // use of SMB network based file systems may result in unsuccesful cleanup
144 // of the disk based resource on exit of the VM. The Windows TMP and TEMP
145 // environement variables, as used by the GetTempPath() Win32 API (see
318 //
319 struct dirent* dentry;
320 char* tdbuf = NEW_C_HEAP_ARRAY(char, os::readdir_buf_size(tmpdirname), mtInternal);
321 errno = 0;
322 while ((dentry = os::readdir(tmpdirp, (struct dirent *)tdbuf)) != NULL) {
323
324 // check if the directory entry is a hsperfdata file
325 if (strncmp(dentry->d_name, PERFDATA_NAME, strlen(PERFDATA_NAME)) != 0) {
326 continue;
327 }
328
329 char* usrdir_name = NEW_C_HEAP_ARRAY(char,
330 strlen(tmpdirname) + strlen(dentry->d_name) + 2, mtInternal);
331 strcpy(usrdir_name, tmpdirname);
332 strcat(usrdir_name, "\\");
333 strcat(usrdir_name, dentry->d_name);
334
335 DIR* subdirp = os::opendir(usrdir_name);
336
337 if (subdirp == NULL) {
338 FREE_C_HEAP_ARRAY(char, usrdir_name, mtInternal);
339 continue;
340 }
341
342 // Since we don't create the backing store files in directories
343 // pointed to by symbolic links, we also don't follow them when
344 // looking for the files. We check for a symbolic link after the
345 // call to opendir in order to eliminate a small window where the
346 // symlink can be exploited.
347 //
348 if (!is_directory_secure(usrdir_name)) {
349 FREE_C_HEAP_ARRAY(char, usrdir_name, mtInternal);
350 os::closedir(subdirp);
351 continue;
352 }
353
354 struct dirent* udentry;
355 char* udbuf = NEW_C_HEAP_ARRAY(char, os::readdir_buf_size(usrdir_name), mtInternal);
356 errno = 0;
357 while ((udentry = os::readdir(subdirp, (struct dirent *)udbuf)) != NULL) {
358
359 if (filename_to_pid(udentry->d_name) == vmid) {
360 struct stat statbuf;
361
362 char* filename = NEW_C_HEAP_ARRAY(char,
363 strlen(usrdir_name) + strlen(udentry->d_name) + 2, mtInternal);
364
365 strcpy(filename, usrdir_name);
366 strcat(filename, "\\");
367 strcat(filename, udentry->d_name);
368
369 if (::stat(filename, &statbuf) == OS_ERR) {
370 FREE_C_HEAP_ARRAY(char, filename, mtInternal);
371 continue;
372 }
373
374 // skip over files that are not regular files.
375 if ((statbuf.st_mode & S_IFMT) != S_IFREG) {
376 FREE_C_HEAP_ARRAY(char, filename, mtInternal);
377 continue;
378 }
379
380 // If we found a matching file with a newer creation time, then
381 // save the user name. The newer creation time indicates that
382 // we found a newer incarnation of the process associated with
383 // vmid. Due to the way that Windows recycles pids and the fact
384 // that we can't delete the file from the file system namespace
385 // until last close, it is possible for there to be more than
386 // one hsperfdata file with a name matching vmid (diff users).
387 //
388 // We no longer ignore hsperfdata files where (st_size == 0).
389 // In this function, all we're trying to do is determine the
390 // name of the user that owns the process associated with vmid
391 // so the size doesn't matter. Very rarely, we have observed
392 // hsperfdata files where (st_size == 0) and the st_size field
393 // later becomes the expected value.
394 //
395 if (statbuf.st_ctime > latest_ctime) {
396 char* user = strchr(dentry->d_name, '_') + 1;
397
398 if (latest_user != NULL) FREE_C_HEAP_ARRAY(char, latest_user, mtInternal);
399 latest_user = NEW_C_HEAP_ARRAY(char, strlen(user)+1, mtInternal);
400
401 strcpy(latest_user, user);
402 latest_ctime = statbuf.st_ctime;
403 }
404
405 FREE_C_HEAP_ARRAY(char, filename, mtInternal);
406 }
407 }
408 os::closedir(subdirp);
409 FREE_C_HEAP_ARRAY(char, udbuf, mtInternal);
410 FREE_C_HEAP_ARRAY(char, usrdir_name, mtInternal);
411 }
412 os::closedir(tmpdirp);
413 FREE_C_HEAP_ARRAY(char, tdbuf, mtInternal);
414
415 return(latest_user);
416 }
417
418 // return the name of the user that owns the process identified by vmid.
419 //
420 // note: this method should only be used via the Perf native methods.
421 // There are various costs to this method and limiting its use to the
422 // Perf native methods limits the impact to monitoring applications only.
423 //
424 static char* get_user_name(int vmid) {
425
426 // A fast implementation is not provided at this time. It's possible
427 // to provide a fast process id to user name mapping function using
428 // the win32 apis, but the default ACL for the process object only
429 // allows processes with the same owner SID to acquire the process
430 // handle (via OpenProcess(PROCESS_QUERY_INFORMATION)). It's possible
431 // to have the JVM change the ACL for the process object to allow arbitrary
432 // users to access the process handle and the process security token.
433 // The security ramifications need to be studied before providing this
485 // method may be unsuccessful in removing the file.
486 //
487 static void remove_file(const char* dirname, const char* filename) {
488
489 size_t nbytes = strlen(dirname) + strlen(filename) + 2;
490 char* path = NEW_C_HEAP_ARRAY(char, nbytes, mtInternal);
491
492 strcpy(path, dirname);
493 strcat(path, "\\");
494 strcat(path, filename);
495
496 if (::unlink(path) == OS_ERR) {
497 if (PrintMiscellaneous && Verbose) {
498 if (errno != ENOENT) {
499 warning("Could not unlink shared memory backing"
500 " store file %s : %s\n", path, strerror(errno));
501 }
502 }
503 }
504
505 FREE_C_HEAP_ARRAY(char, path, mtInternal);
506 }
507
508 // returns true if the process represented by pid is alive, otherwise
509 // returns false. the validity of the result is only accurate if the
510 // target process is owned by the same principal that owns this process.
511 // this method should not be used if to test the status of an otherwise
512 // arbitrary process unless it is know that this process has the appropriate
513 // privileges to guarantee a result valid.
514 //
515 static bool is_alive(int pid) {
516
517 HANDLE ph = OpenProcess(PROCESS_QUERY_INFORMATION, FALSE, pid);
518 if (ph == NULL) {
519 // the process does not exist.
520 if (PrintMiscellaneous && Verbose) {
521 DWORD lastError = GetLastError();
522 if (lastError != ERROR_INVALID_PARAMETER) {
523 warning("OpenProcess failed: %d\n", GetLastError());
524 }
525 }
666 // process liveness is detected by checking the exit status
667 // of the process. if the process id is valid and the exit status
668 // indicates that it is still running, the file file resources
669 // are not removed. If the process id is invalid, or if we don't
670 // have permissions to check the process status, or if the process
671 // id is valid and the process has terminated, the the file resources
672 // are assumed to be stale and are removed.
673 //
674 if (pid == os::current_process_id() || !is_alive(pid)) {
675
676 // we can only remove the file resources. Any mapped views
677 // of the file can only be unmapped by the processes that
678 // opened those views and the file mapping object will not
679 // get removed until all views are unmapped.
680 //
681 remove_file(dirname, entry->d_name);
682 }
683 errno = 0;
684 }
685 os::closedir(dirp);
686 FREE_C_HEAP_ARRAY(char, dbuf, mtInternal);
687 }
688
689 // create a file mapping object with the requested name, and size
690 // from the file represented by the given Handle object
691 //
692 static HANDLE create_file_mapping(const char* name, HANDLE fh, LPSECURITY_ATTRIBUTES fsa, size_t size) {
693
694 DWORD lowSize = (DWORD)size;
695 DWORD highSize = 0;
696 HANDLE fmh = NULL;
697
698 // Create a file mapping object with the given name. This function
699 // will grow the file to the specified size.
700 //
701 fmh = CreateFileMapping(
702 fh, /* HANDLE file handle for backing store */
703 fsa, /* LPSECURITY_ATTRIBUTES Not inheritable */
704 PAGE_READWRITE, /* DWORD protections */
705 highSize, /* DWORD High word of max size */
706 lowSize, /* DWORD Low word of max size */
732 }
733
734
735 // method to free the given security descriptor and the contained
736 // access control list.
737 //
738 static void free_security_desc(PSECURITY_DESCRIPTOR pSD) {
739
740 BOOL success, exists, isdefault;
741 PACL pACL;
742
743 if (pSD != NULL) {
744
745 // get the access control list from the security descriptor
746 success = GetSecurityDescriptorDacl(pSD, &exists, &pACL, &isdefault);
747
748 // if an ACL existed and it was not a default acl, then it must
749 // be an ACL we enlisted. free the resources.
750 //
751 if (success && exists && pACL != NULL && !isdefault) {
752 FREE_C_HEAP_ARRAY(char, pACL, mtInternal);
753 }
754
755 // free the security descriptor
756 FREE_C_HEAP_ARRAY(char, pSD, mtInternal);
757 }
758 }
759
760 // method to free up a security attributes structure and any
761 // contained security descriptors and ACL
762 //
763 static void free_security_attr(LPSECURITY_ATTRIBUTES lpSA) {
764
765 if (lpSA != NULL) {
766 // free the contained security descriptor and the ACL
767 free_security_desc(lpSA->lpSecurityDescriptor);
768 lpSA->lpSecurityDescriptor = NULL;
769
770 // free the security attributes structure
771 FREE_C_HEAP_ARRAY(char, lpSA, mtInternal);
772 }
773 }
774
775 // get the user SID for the process indicated by the process handle
776 //
777 static PSID get_user_sid(HANDLE hProcess) {
778
779 HANDLE hAccessToken;
780 PTOKEN_USER token_buf = NULL;
781 DWORD rsize = 0;
782
783 if (hProcess == NULL) {
784 return NULL;
785 }
786
787 // get the process token
788 if (!OpenProcessToken(hProcess, TOKEN_READ, &hAccessToken)) {
789 if (PrintMiscellaneous && Verbose) {
790 warning("OpenProcessToken failure: lasterror = %d \n", GetLastError());
791 }
798 if (!GetTokenInformation(hAccessToken, TokenUser, NULL, rsize, &rsize)) {
799 DWORD lasterror = GetLastError();
800 if (lasterror != ERROR_INSUFFICIENT_BUFFER) {
801 if (PrintMiscellaneous && Verbose) {
802 warning("GetTokenInformation failure: lasterror = %d,"
803 " rsize = %d\n", lasterror, rsize);
804 }
805 CloseHandle(hAccessToken);
806 return NULL;
807 }
808 }
809
810 token_buf = (PTOKEN_USER) NEW_C_HEAP_ARRAY(char, rsize, mtInternal);
811
812 // get the user token information
813 if (!GetTokenInformation(hAccessToken, TokenUser, token_buf, rsize, &rsize)) {
814 if (PrintMiscellaneous && Verbose) {
815 warning("GetTokenInformation failure: lasterror = %d,"
816 " rsize = %d\n", GetLastError(), rsize);
817 }
818 FREE_C_HEAP_ARRAY(char, token_buf, mtInternal);
819 CloseHandle(hAccessToken);
820 return NULL;
821 }
822
823 DWORD nbytes = GetLengthSid(token_buf->User.Sid);
824 PSID pSID = NEW_C_HEAP_ARRAY(char, nbytes, mtInternal);
825
826 if (!CopySid(nbytes, pSID, token_buf->User.Sid)) {
827 if (PrintMiscellaneous && Verbose) {
828 warning("GetTokenInformation failure: lasterror = %d,"
829 " rsize = %d\n", GetLastError(), rsize);
830 }
831 FREE_C_HEAP_ARRAY(char, token_buf, mtInternal);
832 FREE_C_HEAP_ARRAY(char, pSID, mtInternal);
833 CloseHandle(hAccessToken);
834 return NULL;
835 }
836
837 // close the access token.
838 CloseHandle(hAccessToken);
839 FREE_C_HEAP_ARRAY(char, token_buf, mtInternal);
840
841 return pSID;
842 }
843
844 // structure used to consolidate access control entry information
845 //
846 typedef struct ace_data {
847 PSID pSid; // SID of the ACE
848 DWORD mask; // mask for the ACE
849 } ace_data_t;
850
851
852 // method to add an allow access control entry with the access rights
853 // indicated in mask for the principal indicated in SID to the given
854 // security descriptor. Much of the DACL handling was adapted from
855 // the example provided here:
856 // http://support.microsoft.com/kb/102102/EN-US/
857 //
858
859 static bool add_allow_aces(PSECURITY_DESCRIPTOR pSD,
903 // compute the size needed for the new ACL
904 // initial size of ACL is sum of the following:
905 // * size of ACL structure.
906 // * size of each ACE structure that ACL is to contain minus the sid
907 // sidStart member (DWORD) of the ACE.
908 // * length of the SID that each ACE is to contain.
909 DWORD newACLsize = aclinfo.AclBytesInUse +
910 (sizeof(ACCESS_ALLOWED_ACE) - sizeof(DWORD)) * ace_count;
911 for (int i = 0; i < ace_count; i++) {
912 assert(aces[i].pSid != 0, "pSid should not be 0");
913 newACLsize += GetLengthSid(aces[i].pSid);
914 }
915
916 // create the new ACL
917 newACL = (PACL) NEW_C_HEAP_ARRAY(char, newACLsize, mtInternal);
918
919 if (!InitializeAcl(newACL, newACLsize, ACL_REVISION)) {
920 if (PrintMiscellaneous && Verbose) {
921 warning("InitializeAcl failure: lasterror = %d \n", GetLastError());
922 }
923 FREE_C_HEAP_ARRAY(char, newACL, mtInternal);
924 return false;
925 }
926
927 unsigned int ace_index = 0;
928 // copy any existing ACEs from the old ACL (if any) to the new ACL.
929 if (aclinfo.AceCount != 0) {
930 while (ace_index < aclinfo.AceCount) {
931 LPVOID ace;
932 if (!GetAce(oldACL, ace_index, &ace)) {
933 if (PrintMiscellaneous && Verbose) {
934 warning("InitializeAcl failure: lasterror = %d \n", GetLastError());
935 }
936 FREE_C_HEAP_ARRAY(char, newACL, mtInternal);
937 return false;
938 }
939 if (((ACCESS_ALLOWED_ACE *)ace)->Header.AceFlags && INHERITED_ACE) {
940 // this is an inherited, allowed ACE; break from loop so we can
941 // add the new access allowed, non-inherited ACE in the correct
942 // position, immediately following all non-inherited ACEs.
943 break;
944 }
945
946 // determine if the SID of this ACE matches any of the SIDs
947 // for which we plan to set ACEs.
948 int matches = 0;
949 for (int i = 0; i < ace_count; i++) {
950 if (EqualSid(aces[i].pSid, &(((ACCESS_ALLOWED_ACE *)ace)->SidStart))) {
951 matches++;
952 break;
953 }
954 }
955
956 // if there are no SID matches, then add this existing ACE to the new ACL
957 if (matches == 0) {
958 if (!AddAce(newACL, ACL_REVISION, MAXDWORD, ace,
959 ((PACE_HEADER)ace)->AceSize)) {
960 if (PrintMiscellaneous && Verbose) {
961 warning("AddAce failure: lasterror = %d \n", GetLastError());
962 }
963 FREE_C_HEAP_ARRAY(char, newACL, mtInternal);
964 return false;
965 }
966 }
967 ace_index++;
968 }
969 }
970
971 // add the passed-in access control entries to the new ACL
972 for (int i = 0; i < ace_count; i++) {
973 if (!AddAccessAllowedAce(newACL, ACL_REVISION,
974 aces[i].mask, aces[i].pSid)) {
975 if (PrintMiscellaneous && Verbose) {
976 warning("AddAccessAllowedAce failure: lasterror = %d \n",
977 GetLastError());
978 }
979 FREE_C_HEAP_ARRAY(char, newACL, mtInternal);
980 return false;
981 }
982 }
983
984 // now copy the rest of the inherited ACEs from the old ACL
985 if (aclinfo.AceCount != 0) {
986 // picking up at ace_index, where we left off in the
987 // previous ace_index loop
988 while (ace_index < aclinfo.AceCount) {
989 LPVOID ace;
990 if (!GetAce(oldACL, ace_index, &ace)) {
991 if (PrintMiscellaneous && Verbose) {
992 warning("InitializeAcl failure: lasterror = %d \n", GetLastError());
993 }
994 FREE_C_HEAP_ARRAY(char, newACL, mtInternal);
995 return false;
996 }
997 if (!AddAce(newACL, ACL_REVISION, MAXDWORD, ace,
998 ((PACE_HEADER)ace)->AceSize)) {
999 if (PrintMiscellaneous && Verbose) {
1000 warning("AddAce failure: lasterror = %d \n", GetLastError());
1001 }
1002 FREE_C_HEAP_ARRAY(char, newACL, mtInternal);
1003 return false;
1004 }
1005 ace_index++;
1006 }
1007 }
1008
1009 // add the new ACL to the security descriptor.
1010 if (!SetSecurityDescriptorDacl(pSD, TRUE, newACL, FALSE)) {
1011 if (PrintMiscellaneous && Verbose) {
1012 warning("SetSecurityDescriptorDacl failure:"
1013 " lasterror = %d \n", GetLastError());
1014 }
1015 FREE_C_HEAP_ARRAY(char, newACL, mtInternal);
1016 return false;
1017 }
1018
1019 // if running on windows 2000 or later, set the automatic inheritance
1020 // control flags.
1021 SetSecurityDescriptorControlFnPtr _SetSecurityDescriptorControl;
1022 _SetSecurityDescriptorControl = (SetSecurityDescriptorControlFnPtr)
1023 GetProcAddress(GetModuleHandle(TEXT("advapi32.dll")),
1024 "SetSecurityDescriptorControl");
1025
1026 if (_SetSecurityDescriptorControl != NULL) {
1027 // We do not want to further propagate inherited DACLs, so making them
1028 // protected prevents that.
1029 if (!_SetSecurityDescriptorControl(pSD, SE_DACL_PROTECTED,
1030 SE_DACL_PROTECTED)) {
1031 if (PrintMiscellaneous && Verbose) {
1032 warning("SetSecurityDescriptorControl failure:"
1033 " lasterror = %d \n", GetLastError());
1034 }
1035 FREE_C_HEAP_ARRAY(char, newACL, mtInternal);
1036 return false;
1037 }
1038 }
1039 // Note, the security descriptor maintains a reference to the newACL, not
1040 // a copy of it. Therefore, the newACL is not freed here. It is freed when
1041 // the security descriptor containing its reference is freed.
1042 //
1043 return true;
1044 }
1045
1046 // method to create a security attributes structure, which contains a
1047 // security descriptor and an access control list comprised of 0 or more
1048 // access control entries. The method take an array of ace_data structures
1049 // that indicate the ACE to be added to the security descriptor.
1050 //
1051 // the caller must free the resources associated with the security
1052 // attributes structure created by this method by calling the
1053 // free_security_attr() method.
1054 //
1055 static LPSECURITY_ATTRIBUTES make_security_attr(ace_data_t aces[], int count) {
1132 PSID everybodySid = NULL;
1133 SID_IDENTIFIER_AUTHORITY SIDAuthEverybody = SECURITY_WORLD_SID_AUTHORITY;
1134
1135 if (!AllocateAndInitializeSid( &SIDAuthEverybody, 1, SECURITY_WORLD_RID,
1136 0, 0, 0, 0, 0, 0, 0, &everybodySid)) {
1137
1138 if (PrintMiscellaneous && Verbose) {
1139 warning("AllocateAndInitializeSid failure: "
1140 "lasterror = %d \n", GetLastError());
1141 }
1142 return NULL;
1143 }
1144
1145 // initialize the ace data for everybody else.
1146 aces[2].pSid = everybodySid;
1147 aces[2].mask = emask;
1148
1149 // create a security attributes structure with access control
1150 // entries as initialized above.
1151 LPSECURITY_ATTRIBUTES lpSA = make_security_attr(aces, 3);
1152 FREE_C_HEAP_ARRAY(char, aces[0].pSid, mtInternal);
1153 FreeSid(everybodySid);
1154 FreeSid(administratorsSid);
1155 return(lpSA);
1156 }
1157
1158
1159 // method to create the security attributes structure for restricting
1160 // access to the user temporary directory.
1161 //
1162 // the caller must free the resources associated with the security
1163 // attributes structure created by this method by calling the
1164 // free_security_attr() method.
1165 //
1166 static LPSECURITY_ATTRIBUTES make_tmpdir_security_attr() {
1167
1168 // create full access rights for the user/owner of the directory
1169 // and read-only access rights for everybody else. This is
1170 // effectively equivalent to UNIX 755 permissions on a directory.
1171 //
1172 DWORD umask = STANDARD_RIGHTS_REQUIRED | FILE_ALL_ACCESS;
1447 // construct the name of the user specific temporary directory
1448 char* dirname = get_user_tmp_dir(user);
1449
1450 // check that the file system is secure - i.e. it supports ACLs.
1451 if (!is_filesystem_secure(dirname)) {
1452 return NULL;
1453 }
1454
1455 // create the names of the backing store files and for the
1456 // share memory object.
1457 //
1458 char* filename = get_sharedmem_filename(dirname, vmid);
1459 char* objectname = get_sharedmem_objectname(user, vmid);
1460
1461 // cleanup any stale shared memory resources
1462 cleanup_sharedmem_resources(dirname);
1463
1464 assert(((size != 0) && (size % os::vm_page_size() == 0)),
1465 "unexpected PerfMemry region size");
1466
1467 FREE_C_HEAP_ARRAY(char, user, mtInternal);
1468
1469 // create the shared memory resources
1470 sharedmem_fileMapHandle =
1471 create_sharedmem_resources(dirname, filename, objectname, size);
1472
1473 FREE_C_HEAP_ARRAY(char, filename, mtInternal);
1474 FREE_C_HEAP_ARRAY(char, objectname, mtInternal);
1475 FREE_C_HEAP_ARRAY(char, dirname, mtInternal);
1476
1477 if (sharedmem_fileMapHandle == NULL) {
1478 return NULL;
1479 }
1480
1481 // map the file into the address space
1482 mapAddress = MapViewOfFile(
1483 sharedmem_fileMapHandle, /* HANDLE = file mapping object */
1484 FILE_MAP_ALL_ACCESS, /* DWORD access flags */
1485 0, /* DWORD High word of offset */
1486 0, /* DWORD Low word of offset */
1487 (DWORD)size); /* DWORD Number of bytes to map */
1488
1489 if (mapAddress == NULL) {
1490 if (PrintMiscellaneous && Verbose) {
1491 warning("MapViewOfFile failed, lasterror = %d\n", GetLastError());
1492 }
1493 CloseHandle(sharedmem_fileMapHandle);
1494 sharedmem_fileMapHandle = NULL;
1495 return NULL;
1610 // the owner of the target vm.
1611 if (user == NULL || strlen(user) == 0) {
1612 luser = get_user_name(vmid);
1613 }
1614 else {
1615 luser = user;
1616 }
1617
1618 if (luser == NULL) {
1619 THROW_MSG(vmSymbols::java_lang_IllegalArgumentException(),
1620 "Could not map vmid to user name");
1621 }
1622
1623 // get the names for the resources for the target vm
1624 char* dirname = get_user_tmp_dir(luser);
1625
1626 // since we don't follow symbolic links when creating the backing
1627 // store file, we also don't following them when attaching
1628 //
1629 if (!is_directory_secure(dirname)) {
1630 FREE_C_HEAP_ARRAY(char, dirname, mtInternal);
1631 THROW_MSG(vmSymbols::java_lang_IllegalArgumentException(),
1632 "Process not found");
1633 }
1634
1635 char* filename = get_sharedmem_filename(dirname, vmid);
1636 char* objectname = get_sharedmem_objectname(luser, vmid);
1637
1638 // copy heap memory to resource memory. the objectname and
1639 // filename are passed to methods that may throw exceptions.
1640 // using resource arrays for these names prevents the leaks
1641 // that would otherwise occur.
1642 //
1643 char* rfilename = NEW_RESOURCE_ARRAY(char, strlen(filename) + 1);
1644 char* robjectname = NEW_RESOURCE_ARRAY(char, strlen(objectname) + 1);
1645 strcpy(rfilename, filename);
1646 strcpy(robjectname, objectname);
1647
1648 // free the c heap resources that are no longer needed
1649 if (luser != user) FREE_C_HEAP_ARRAY(char, luser, mtInternal);
1650 FREE_C_HEAP_ARRAY(char, dirname, mtInternal);
1651 FREE_C_HEAP_ARRAY(char, filename, mtInternal);
1652 FREE_C_HEAP_ARRAY(char, objectname, mtInternal);
1653
1654 if (*sizep == 0) {
1655 size = sharedmem_filesize(rfilename, CHECK);
1656 } else {
1657 size = *sizep;
1658 }
1659
1660 assert(size > 0, "unexpected size <= 0");
1661
1662 // Open the file mapping object with the given name
1663 fmh = open_sharedmem_object(robjectname, ofm_access, CHECK);
1664
1665 assert(fmh != INVALID_HANDLE_VALUE, "unexpected handle value");
1666
1667 // map the entire file into the address space
1668 mapAddress = MapViewOfFile(
1669 fmh, /* HANDLE Handle of file mapping object */
1670 mv_access, /* DWORD access flags */
1671 0, /* DWORD High word of offset */
1672 0, /* DWORD Low word of offset */
|
105 if (nbytes == OS_ERR) {
106 if (PrintMiscellaneous && Verbose) {
107 warning("Could not write Perfdata save file: %s: %s\n",
108 destfile, strerror(errno));
109 }
110 break;
111 }
112
113 remaining -= (size_t)nbytes;
114 addr += nbytes;
115 }
116
117 int result = ::_close(fd);
118 if (PrintMiscellaneous && Verbose) {
119 if (result == OS_ERR) {
120 warning("Could not close %s: %s\n", destfile, strerror(errno));
121 }
122 }
123 }
124
125 FREE_C_HEAP_ARRAY(char, destfile);
126 }
127
128 // Shared Memory Implementation Details
129
130 // Note: the win32 shared memory implementation uses two objects to represent
131 // the shared memory: a windows kernel based file mapping object and a backing
132 // store file. On windows, the name space for shared memory is a kernel
133 // based name space that is disjoint from other win32 name spaces. Since Java
134 // is unaware of this name space, a parallel file system based name space is
135 // maintained, which provides a common file system based shared memory name
136 // space across the supported platforms and one that Java apps can deal with
137 // through simple file apis.
138 //
139 // For performance and resource cleanup reasons, it is recommended that the
140 // user specific directory and the backing store file be stored in either a
141 // RAM based file system or a local disk based file system. Network based
142 // file systems are not recommended for performance reasons. In addition,
143 // use of SMB network based file systems may result in unsuccesful cleanup
144 // of the disk based resource on exit of the VM. The Windows TMP and TEMP
145 // environement variables, as used by the GetTempPath() Win32 API (see
318 //
319 struct dirent* dentry;
320 char* tdbuf = NEW_C_HEAP_ARRAY(char, os::readdir_buf_size(tmpdirname), mtInternal);
321 errno = 0;
322 while ((dentry = os::readdir(tmpdirp, (struct dirent *)tdbuf)) != NULL) {
323
324 // check if the directory entry is a hsperfdata file
325 if (strncmp(dentry->d_name, PERFDATA_NAME, strlen(PERFDATA_NAME)) != 0) {
326 continue;
327 }
328
329 char* usrdir_name = NEW_C_HEAP_ARRAY(char,
330 strlen(tmpdirname) + strlen(dentry->d_name) + 2, mtInternal);
331 strcpy(usrdir_name, tmpdirname);
332 strcat(usrdir_name, "\\");
333 strcat(usrdir_name, dentry->d_name);
334
335 DIR* subdirp = os::opendir(usrdir_name);
336
337 if (subdirp == NULL) {
338 FREE_C_HEAP_ARRAY(char, usrdir_name);
339 continue;
340 }
341
342 // Since we don't create the backing store files in directories
343 // pointed to by symbolic links, we also don't follow them when
344 // looking for the files. We check for a symbolic link after the
345 // call to opendir in order to eliminate a small window where the
346 // symlink can be exploited.
347 //
348 if (!is_directory_secure(usrdir_name)) {
349 FREE_C_HEAP_ARRAY(char, usrdir_name);
350 os::closedir(subdirp);
351 continue;
352 }
353
354 struct dirent* udentry;
355 char* udbuf = NEW_C_HEAP_ARRAY(char, os::readdir_buf_size(usrdir_name), mtInternal);
356 errno = 0;
357 while ((udentry = os::readdir(subdirp, (struct dirent *)udbuf)) != NULL) {
358
359 if (filename_to_pid(udentry->d_name) == vmid) {
360 struct stat statbuf;
361
362 char* filename = NEW_C_HEAP_ARRAY(char,
363 strlen(usrdir_name) + strlen(udentry->d_name) + 2, mtInternal);
364
365 strcpy(filename, usrdir_name);
366 strcat(filename, "\\");
367 strcat(filename, udentry->d_name);
368
369 if (::stat(filename, &statbuf) == OS_ERR) {
370 FREE_C_HEAP_ARRAY(char, filename);
371 continue;
372 }
373
374 // skip over files that are not regular files.
375 if ((statbuf.st_mode & S_IFMT) != S_IFREG) {
376 FREE_C_HEAP_ARRAY(char, filename);
377 continue;
378 }
379
380 // If we found a matching file with a newer creation time, then
381 // save the user name. The newer creation time indicates that
382 // we found a newer incarnation of the process associated with
383 // vmid. Due to the way that Windows recycles pids and the fact
384 // that we can't delete the file from the file system namespace
385 // until last close, it is possible for there to be more than
386 // one hsperfdata file with a name matching vmid (diff users).
387 //
388 // We no longer ignore hsperfdata files where (st_size == 0).
389 // In this function, all we're trying to do is determine the
390 // name of the user that owns the process associated with vmid
391 // so the size doesn't matter. Very rarely, we have observed
392 // hsperfdata files where (st_size == 0) and the st_size field
393 // later becomes the expected value.
394 //
395 if (statbuf.st_ctime > latest_ctime) {
396 char* user = strchr(dentry->d_name, '_') + 1;
397
398 if (latest_user != NULL) FREE_C_HEAP_ARRAY(char, latest_user);
399 latest_user = NEW_C_HEAP_ARRAY(char, strlen(user)+1, mtInternal);
400
401 strcpy(latest_user, user);
402 latest_ctime = statbuf.st_ctime;
403 }
404
405 FREE_C_HEAP_ARRAY(char, filename);
406 }
407 }
408 os::closedir(subdirp);
409 FREE_C_HEAP_ARRAY(char, udbuf);
410 FREE_C_HEAP_ARRAY(char, usrdir_name);
411 }
412 os::closedir(tmpdirp);
413 FREE_C_HEAP_ARRAY(char, tdbuf);
414
415 return(latest_user);
416 }
417
418 // return the name of the user that owns the process identified by vmid.
419 //
420 // note: this method should only be used via the Perf native methods.
421 // There are various costs to this method and limiting its use to the
422 // Perf native methods limits the impact to monitoring applications only.
423 //
424 static char* get_user_name(int vmid) {
425
426 // A fast implementation is not provided at this time. It's possible
427 // to provide a fast process id to user name mapping function using
428 // the win32 apis, but the default ACL for the process object only
429 // allows processes with the same owner SID to acquire the process
430 // handle (via OpenProcess(PROCESS_QUERY_INFORMATION)). It's possible
431 // to have the JVM change the ACL for the process object to allow arbitrary
432 // users to access the process handle and the process security token.
433 // The security ramifications need to be studied before providing this
485 // method may be unsuccessful in removing the file.
486 //
487 static void remove_file(const char* dirname, const char* filename) {
488
489 size_t nbytes = strlen(dirname) + strlen(filename) + 2;
490 char* path = NEW_C_HEAP_ARRAY(char, nbytes, mtInternal);
491
492 strcpy(path, dirname);
493 strcat(path, "\\");
494 strcat(path, filename);
495
496 if (::unlink(path) == OS_ERR) {
497 if (PrintMiscellaneous && Verbose) {
498 if (errno != ENOENT) {
499 warning("Could not unlink shared memory backing"
500 " store file %s : %s\n", path, strerror(errno));
501 }
502 }
503 }
504
505 FREE_C_HEAP_ARRAY(char, path);
506 }
507
508 // returns true if the process represented by pid is alive, otherwise
509 // returns false. the validity of the result is only accurate if the
510 // target process is owned by the same principal that owns this process.
511 // this method should not be used if to test the status of an otherwise
512 // arbitrary process unless it is know that this process has the appropriate
513 // privileges to guarantee a result valid.
514 //
515 static bool is_alive(int pid) {
516
517 HANDLE ph = OpenProcess(PROCESS_QUERY_INFORMATION, FALSE, pid);
518 if (ph == NULL) {
519 // the process does not exist.
520 if (PrintMiscellaneous && Verbose) {
521 DWORD lastError = GetLastError();
522 if (lastError != ERROR_INVALID_PARAMETER) {
523 warning("OpenProcess failed: %d\n", GetLastError());
524 }
525 }
666 // process liveness is detected by checking the exit status
667 // of the process. if the process id is valid and the exit status
668 // indicates that it is still running, the file file resources
669 // are not removed. If the process id is invalid, or if we don't
670 // have permissions to check the process status, or if the process
671 // id is valid and the process has terminated, the the file resources
672 // are assumed to be stale and are removed.
673 //
674 if (pid == os::current_process_id() || !is_alive(pid)) {
675
676 // we can only remove the file resources. Any mapped views
677 // of the file can only be unmapped by the processes that
678 // opened those views and the file mapping object will not
679 // get removed until all views are unmapped.
680 //
681 remove_file(dirname, entry->d_name);
682 }
683 errno = 0;
684 }
685 os::closedir(dirp);
686 FREE_C_HEAP_ARRAY(char, dbuf);
687 }
688
689 // create a file mapping object with the requested name, and size
690 // from the file represented by the given Handle object
691 //
692 static HANDLE create_file_mapping(const char* name, HANDLE fh, LPSECURITY_ATTRIBUTES fsa, size_t size) {
693
694 DWORD lowSize = (DWORD)size;
695 DWORD highSize = 0;
696 HANDLE fmh = NULL;
697
698 // Create a file mapping object with the given name. This function
699 // will grow the file to the specified size.
700 //
701 fmh = CreateFileMapping(
702 fh, /* HANDLE file handle for backing store */
703 fsa, /* LPSECURITY_ATTRIBUTES Not inheritable */
704 PAGE_READWRITE, /* DWORD protections */
705 highSize, /* DWORD High word of max size */
706 lowSize, /* DWORD Low word of max size */
732 }
733
734
735 // method to free the given security descriptor and the contained
736 // access control list.
737 //
738 static void free_security_desc(PSECURITY_DESCRIPTOR pSD) {
739
740 BOOL success, exists, isdefault;
741 PACL pACL;
742
743 if (pSD != NULL) {
744
745 // get the access control list from the security descriptor
746 success = GetSecurityDescriptorDacl(pSD, &exists, &pACL, &isdefault);
747
748 // if an ACL existed and it was not a default acl, then it must
749 // be an ACL we enlisted. free the resources.
750 //
751 if (success && exists && pACL != NULL && !isdefault) {
752 FREE_C_HEAP_ARRAY(char, pACL);
753 }
754
755 // free the security descriptor
756 FREE_C_HEAP_ARRAY(char, pSD);
757 }
758 }
759
760 // method to free up a security attributes structure and any
761 // contained security descriptors and ACL
762 //
763 static void free_security_attr(LPSECURITY_ATTRIBUTES lpSA) {
764
765 if (lpSA != NULL) {
766 // free the contained security descriptor and the ACL
767 free_security_desc(lpSA->lpSecurityDescriptor);
768 lpSA->lpSecurityDescriptor = NULL;
769
770 // free the security attributes structure
771 FREE_C_HEAP_ARRAY(char, lpSA);
772 }
773 }
774
775 // get the user SID for the process indicated by the process handle
776 //
777 static PSID get_user_sid(HANDLE hProcess) {
778
779 HANDLE hAccessToken;
780 PTOKEN_USER token_buf = NULL;
781 DWORD rsize = 0;
782
783 if (hProcess == NULL) {
784 return NULL;
785 }
786
787 // get the process token
788 if (!OpenProcessToken(hProcess, TOKEN_READ, &hAccessToken)) {
789 if (PrintMiscellaneous && Verbose) {
790 warning("OpenProcessToken failure: lasterror = %d \n", GetLastError());
791 }
798 if (!GetTokenInformation(hAccessToken, TokenUser, NULL, rsize, &rsize)) {
799 DWORD lasterror = GetLastError();
800 if (lasterror != ERROR_INSUFFICIENT_BUFFER) {
801 if (PrintMiscellaneous && Verbose) {
802 warning("GetTokenInformation failure: lasterror = %d,"
803 " rsize = %d\n", lasterror, rsize);
804 }
805 CloseHandle(hAccessToken);
806 return NULL;
807 }
808 }
809
810 token_buf = (PTOKEN_USER) NEW_C_HEAP_ARRAY(char, rsize, mtInternal);
811
812 // get the user token information
813 if (!GetTokenInformation(hAccessToken, TokenUser, token_buf, rsize, &rsize)) {
814 if (PrintMiscellaneous && Verbose) {
815 warning("GetTokenInformation failure: lasterror = %d,"
816 " rsize = %d\n", GetLastError(), rsize);
817 }
818 FREE_C_HEAP_ARRAY(char, token_buf);
819 CloseHandle(hAccessToken);
820 return NULL;
821 }
822
823 DWORD nbytes = GetLengthSid(token_buf->User.Sid);
824 PSID pSID = NEW_C_HEAP_ARRAY(char, nbytes, mtInternal);
825
826 if (!CopySid(nbytes, pSID, token_buf->User.Sid)) {
827 if (PrintMiscellaneous && Verbose) {
828 warning("GetTokenInformation failure: lasterror = %d,"
829 " rsize = %d\n", GetLastError(), rsize);
830 }
831 FREE_C_HEAP_ARRAY(char, token_buf);
832 FREE_C_HEAP_ARRAY(char, pSID);
833 CloseHandle(hAccessToken);
834 return NULL;
835 }
836
837 // close the access token.
838 CloseHandle(hAccessToken);
839 FREE_C_HEAP_ARRAY(char, token_buf);
840
841 return pSID;
842 }
843
844 // structure used to consolidate access control entry information
845 //
846 typedef struct ace_data {
847 PSID pSid; // SID of the ACE
848 DWORD mask; // mask for the ACE
849 } ace_data_t;
850
851
852 // method to add an allow access control entry with the access rights
853 // indicated in mask for the principal indicated in SID to the given
854 // security descriptor. Much of the DACL handling was adapted from
855 // the example provided here:
856 // http://support.microsoft.com/kb/102102/EN-US/
857 //
858
859 static bool add_allow_aces(PSECURITY_DESCRIPTOR pSD,
903 // compute the size needed for the new ACL
904 // initial size of ACL is sum of the following:
905 // * size of ACL structure.
906 // * size of each ACE structure that ACL is to contain minus the sid
907 // sidStart member (DWORD) of the ACE.
908 // * length of the SID that each ACE is to contain.
909 DWORD newACLsize = aclinfo.AclBytesInUse +
910 (sizeof(ACCESS_ALLOWED_ACE) - sizeof(DWORD)) * ace_count;
911 for (int i = 0; i < ace_count; i++) {
912 assert(aces[i].pSid != 0, "pSid should not be 0");
913 newACLsize += GetLengthSid(aces[i].pSid);
914 }
915
916 // create the new ACL
917 newACL = (PACL) NEW_C_HEAP_ARRAY(char, newACLsize, mtInternal);
918
919 if (!InitializeAcl(newACL, newACLsize, ACL_REVISION)) {
920 if (PrintMiscellaneous && Verbose) {
921 warning("InitializeAcl failure: lasterror = %d \n", GetLastError());
922 }
923 FREE_C_HEAP_ARRAY(char, newACL);
924 return false;
925 }
926
927 unsigned int ace_index = 0;
928 // copy any existing ACEs from the old ACL (if any) to the new ACL.
929 if (aclinfo.AceCount != 0) {
930 while (ace_index < aclinfo.AceCount) {
931 LPVOID ace;
932 if (!GetAce(oldACL, ace_index, &ace)) {
933 if (PrintMiscellaneous && Verbose) {
934 warning("InitializeAcl failure: lasterror = %d \n", GetLastError());
935 }
936 FREE_C_HEAP_ARRAY(char, newACL);
937 return false;
938 }
939 if (((ACCESS_ALLOWED_ACE *)ace)->Header.AceFlags && INHERITED_ACE) {
940 // this is an inherited, allowed ACE; break from loop so we can
941 // add the new access allowed, non-inherited ACE in the correct
942 // position, immediately following all non-inherited ACEs.
943 break;
944 }
945
946 // determine if the SID of this ACE matches any of the SIDs
947 // for which we plan to set ACEs.
948 int matches = 0;
949 for (int i = 0; i < ace_count; i++) {
950 if (EqualSid(aces[i].pSid, &(((ACCESS_ALLOWED_ACE *)ace)->SidStart))) {
951 matches++;
952 break;
953 }
954 }
955
956 // if there are no SID matches, then add this existing ACE to the new ACL
957 if (matches == 0) {
958 if (!AddAce(newACL, ACL_REVISION, MAXDWORD, ace,
959 ((PACE_HEADER)ace)->AceSize)) {
960 if (PrintMiscellaneous && Verbose) {
961 warning("AddAce failure: lasterror = %d \n", GetLastError());
962 }
963 FREE_C_HEAP_ARRAY(char, newACL);
964 return false;
965 }
966 }
967 ace_index++;
968 }
969 }
970
971 // add the passed-in access control entries to the new ACL
972 for (int i = 0; i < ace_count; i++) {
973 if (!AddAccessAllowedAce(newACL, ACL_REVISION,
974 aces[i].mask, aces[i].pSid)) {
975 if (PrintMiscellaneous && Verbose) {
976 warning("AddAccessAllowedAce failure: lasterror = %d \n",
977 GetLastError());
978 }
979 FREE_C_HEAP_ARRAY(char, newACL);
980 return false;
981 }
982 }
983
984 // now copy the rest of the inherited ACEs from the old ACL
985 if (aclinfo.AceCount != 0) {
986 // picking up at ace_index, where we left off in the
987 // previous ace_index loop
988 while (ace_index < aclinfo.AceCount) {
989 LPVOID ace;
990 if (!GetAce(oldACL, ace_index, &ace)) {
991 if (PrintMiscellaneous && Verbose) {
992 warning("InitializeAcl failure: lasterror = %d \n", GetLastError());
993 }
994 FREE_C_HEAP_ARRAY(char, newACL);
995 return false;
996 }
997 if (!AddAce(newACL, ACL_REVISION, MAXDWORD, ace,
998 ((PACE_HEADER)ace)->AceSize)) {
999 if (PrintMiscellaneous && Verbose) {
1000 warning("AddAce failure: lasterror = %d \n", GetLastError());
1001 }
1002 FREE_C_HEAP_ARRAY(char, newACL);
1003 return false;
1004 }
1005 ace_index++;
1006 }
1007 }
1008
1009 // add the new ACL to the security descriptor.
1010 if (!SetSecurityDescriptorDacl(pSD, TRUE, newACL, FALSE)) {
1011 if (PrintMiscellaneous && Verbose) {
1012 warning("SetSecurityDescriptorDacl failure:"
1013 " lasterror = %d \n", GetLastError());
1014 }
1015 FREE_C_HEAP_ARRAY(char, newACL);
1016 return false;
1017 }
1018
1019 // if running on windows 2000 or later, set the automatic inheritance
1020 // control flags.
1021 SetSecurityDescriptorControlFnPtr _SetSecurityDescriptorControl;
1022 _SetSecurityDescriptorControl = (SetSecurityDescriptorControlFnPtr)
1023 GetProcAddress(GetModuleHandle(TEXT("advapi32.dll")),
1024 "SetSecurityDescriptorControl");
1025
1026 if (_SetSecurityDescriptorControl != NULL) {
1027 // We do not want to further propagate inherited DACLs, so making them
1028 // protected prevents that.
1029 if (!_SetSecurityDescriptorControl(pSD, SE_DACL_PROTECTED,
1030 SE_DACL_PROTECTED)) {
1031 if (PrintMiscellaneous && Verbose) {
1032 warning("SetSecurityDescriptorControl failure:"
1033 " lasterror = %d \n", GetLastError());
1034 }
1035 FREE_C_HEAP_ARRAY(char, newACL);
1036 return false;
1037 }
1038 }
1039 // Note, the security descriptor maintains a reference to the newACL, not
1040 // a copy of it. Therefore, the newACL is not freed here. It is freed when
1041 // the security descriptor containing its reference is freed.
1042 //
1043 return true;
1044 }
1045
1046 // method to create a security attributes structure, which contains a
1047 // security descriptor and an access control list comprised of 0 or more
1048 // access control entries. The method take an array of ace_data structures
1049 // that indicate the ACE to be added to the security descriptor.
1050 //
1051 // the caller must free the resources associated with the security
1052 // attributes structure created by this method by calling the
1053 // free_security_attr() method.
1054 //
1055 static LPSECURITY_ATTRIBUTES make_security_attr(ace_data_t aces[], int count) {
1132 PSID everybodySid = NULL;
1133 SID_IDENTIFIER_AUTHORITY SIDAuthEverybody = SECURITY_WORLD_SID_AUTHORITY;
1134
1135 if (!AllocateAndInitializeSid( &SIDAuthEverybody, 1, SECURITY_WORLD_RID,
1136 0, 0, 0, 0, 0, 0, 0, &everybodySid)) {
1137
1138 if (PrintMiscellaneous && Verbose) {
1139 warning("AllocateAndInitializeSid failure: "
1140 "lasterror = %d \n", GetLastError());
1141 }
1142 return NULL;
1143 }
1144
1145 // initialize the ace data for everybody else.
1146 aces[2].pSid = everybodySid;
1147 aces[2].mask = emask;
1148
1149 // create a security attributes structure with access control
1150 // entries as initialized above.
1151 LPSECURITY_ATTRIBUTES lpSA = make_security_attr(aces, 3);
1152 FREE_C_HEAP_ARRAY(char, aces[0].pSid);
1153 FreeSid(everybodySid);
1154 FreeSid(administratorsSid);
1155 return(lpSA);
1156 }
1157
1158
1159 // method to create the security attributes structure for restricting
1160 // access to the user temporary directory.
1161 //
1162 // the caller must free the resources associated with the security
1163 // attributes structure created by this method by calling the
1164 // free_security_attr() method.
1165 //
1166 static LPSECURITY_ATTRIBUTES make_tmpdir_security_attr() {
1167
1168 // create full access rights for the user/owner of the directory
1169 // and read-only access rights for everybody else. This is
1170 // effectively equivalent to UNIX 755 permissions on a directory.
1171 //
1172 DWORD umask = STANDARD_RIGHTS_REQUIRED | FILE_ALL_ACCESS;
1447 // construct the name of the user specific temporary directory
1448 char* dirname = get_user_tmp_dir(user);
1449
1450 // check that the file system is secure - i.e. it supports ACLs.
1451 if (!is_filesystem_secure(dirname)) {
1452 return NULL;
1453 }
1454
1455 // create the names of the backing store files and for the
1456 // share memory object.
1457 //
1458 char* filename = get_sharedmem_filename(dirname, vmid);
1459 char* objectname = get_sharedmem_objectname(user, vmid);
1460
1461 // cleanup any stale shared memory resources
1462 cleanup_sharedmem_resources(dirname);
1463
1464 assert(((size != 0) && (size % os::vm_page_size() == 0)),
1465 "unexpected PerfMemry region size");
1466
1467 FREE_C_HEAP_ARRAY(char, user);
1468
1469 // create the shared memory resources
1470 sharedmem_fileMapHandle =
1471 create_sharedmem_resources(dirname, filename, objectname, size);
1472
1473 FREE_C_HEAP_ARRAY(char, filename);
1474 FREE_C_HEAP_ARRAY(char, objectname);
1475 FREE_C_HEAP_ARRAY(char, dirname);
1476
1477 if (sharedmem_fileMapHandle == NULL) {
1478 return NULL;
1479 }
1480
1481 // map the file into the address space
1482 mapAddress = MapViewOfFile(
1483 sharedmem_fileMapHandle, /* HANDLE = file mapping object */
1484 FILE_MAP_ALL_ACCESS, /* DWORD access flags */
1485 0, /* DWORD High word of offset */
1486 0, /* DWORD Low word of offset */
1487 (DWORD)size); /* DWORD Number of bytes to map */
1488
1489 if (mapAddress == NULL) {
1490 if (PrintMiscellaneous && Verbose) {
1491 warning("MapViewOfFile failed, lasterror = %d\n", GetLastError());
1492 }
1493 CloseHandle(sharedmem_fileMapHandle);
1494 sharedmem_fileMapHandle = NULL;
1495 return NULL;
1610 // the owner of the target vm.
1611 if (user == NULL || strlen(user) == 0) {
1612 luser = get_user_name(vmid);
1613 }
1614 else {
1615 luser = user;
1616 }
1617
1618 if (luser == NULL) {
1619 THROW_MSG(vmSymbols::java_lang_IllegalArgumentException(),
1620 "Could not map vmid to user name");
1621 }
1622
1623 // get the names for the resources for the target vm
1624 char* dirname = get_user_tmp_dir(luser);
1625
1626 // since we don't follow symbolic links when creating the backing
1627 // store file, we also don't following them when attaching
1628 //
1629 if (!is_directory_secure(dirname)) {
1630 FREE_C_HEAP_ARRAY(char, dirname);
1631 THROW_MSG(vmSymbols::java_lang_IllegalArgumentException(),
1632 "Process not found");
1633 }
1634
1635 char* filename = get_sharedmem_filename(dirname, vmid);
1636 char* objectname = get_sharedmem_objectname(luser, vmid);
1637
1638 // copy heap memory to resource memory. the objectname and
1639 // filename are passed to methods that may throw exceptions.
1640 // using resource arrays for these names prevents the leaks
1641 // that would otherwise occur.
1642 //
1643 char* rfilename = NEW_RESOURCE_ARRAY(char, strlen(filename) + 1);
1644 char* robjectname = NEW_RESOURCE_ARRAY(char, strlen(objectname) + 1);
1645 strcpy(rfilename, filename);
1646 strcpy(robjectname, objectname);
1647
1648 // free the c heap resources that are no longer needed
1649 if (luser != user) FREE_C_HEAP_ARRAY(char, luser);
1650 FREE_C_HEAP_ARRAY(char, dirname);
1651 FREE_C_HEAP_ARRAY(char, filename);
1652 FREE_C_HEAP_ARRAY(char, objectname);
1653
1654 if (*sizep == 0) {
1655 size = sharedmem_filesize(rfilename, CHECK);
1656 } else {
1657 size = *sizep;
1658 }
1659
1660 assert(size > 0, "unexpected size <= 0");
1661
1662 // Open the file mapping object with the given name
1663 fmh = open_sharedmem_object(robjectname, ofm_access, CHECK);
1664
1665 assert(fmh != INVALID_HANDLE_VALUE, "unexpected handle value");
1666
1667 // map the entire file into the address space
1668 mapAddress = MapViewOfFile(
1669 fmh, /* HANDLE Handle of file mapping object */
1670 mv_access, /* DWORD access flags */
1671 0, /* DWORD High word of offset */
1672 0, /* DWORD Low word of offset */
|