Changeset 10008 in vbox for trunk/src/VBox/Additions/WINNT/VBoxControl
- Timestamp:
- Jun 27, 2008 9:43:38 PM (17 years ago)
- Location:
- trunk/src/VBox/Additions/WINNT/VBoxControl
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Additions/WINNT/VBoxControl/Makefile.kmk
r9664 r10008 34 34 35 35 # VBoxControl.cpp uses VBOX_SVN_REV. 36 VBoxControl.cpp_DEFS += VBOX_SVN_REV=$(VBOX_SVN_REV) 36 VBoxControl.cpp_DEFS += VBOX_SVN_REV=$(VBOX_SVN_REV) VBOX_HGCM 37 37 VBoxControl.cpp_DEPS = $(VBOX_SVN_REV_KMK) 38 38 -
trunk/src/VBox/Additions/WINNT/VBoxControl/VBoxControl.cpp
r8155 r10008 25 25 #include <VBox/VBoxGuest.h> 26 26 #include <VBox/version.h> 27 #include <VBox/HostServices/VBoxInfoSvc.h> 27 28 28 29 void printHelp() … … 40 41 "VBoxControl removecustommode <width> <height> <bpp>\n" 41 42 "\n" 42 "VBoxControl setvideomode <width> <height> <bpp> <screen>\n"); 43 "VBoxControl setvideomode <width> <height> <bpp> <screen>\n" 44 "\n" 45 "VBoxControl getguestproperty <key>\n" 46 "\n" 47 "VBoxControl setguestproperty <key> [<value>] (no value to delete)\n"); 43 48 } 44 49 … … 779 784 780 785 /** 786 * Open the VirtualBox guest device. 787 * @returns IPRT status value 788 * @param hDevice where to store the handle to the open device 789 */ 790 static int openGuestDevice(HANDLE *hDevice) 791 { 792 if (!VALID_PTR(hDevice)) 793 return VERR_INVALID_POINTER; 794 *hDevice = CreateFile(VBOXGUEST_DEVICE_NAME, 795 GENERIC_READ | GENERIC_WRITE, 796 FILE_SHARE_READ | FILE_SHARE_WRITE, 797 NULL, 798 OPEN_EXISTING, 799 FILE_ATTRIBUTE_NORMAL, 800 NULL); 801 return (*hDevice != INVALID_HANDLE_VALUE) ? VINF_SUCCESS : VERR_OPEN_FAILED; 802 } 803 804 805 /** 806 * Connect to an HGCM service. 807 * @returns IPRT status code 808 * @param hDevice handle to the VBox device 809 * @param pszService the name of the service to connect to 810 * @param pu32ClientID where to store the connection handle 811 */ 812 static int hgcmConnect(HANDLE hDevice, char *pszService, uint32_t *pu32ClientID) 813 { 814 if (!VALID_PTR(pszService) || !VALID_PTR(pu32ClientID)) 815 return VERR_INVALID_POINTER; 816 VBoxGuestHGCMConnectInfo info; 817 int rc = VINF_SUCCESS; 818 819 memset (&info, 0, sizeof (info)); 820 if (strlen(pszService) + 1 > sizeof(info.Loc.u.host.achName)) 821 return false; 822 strcpy (info.Loc.u.host.achName, pszService); 823 info.Loc.type = VMMDevHGCMLoc_LocalHost_Existing; 824 DWORD cbReturned; 825 if (DeviceIoControl (hDevice, 826 IOCTL_VBOXGUEST_HGCM_CONNECT, 827 &info, sizeof (info), 828 &info, sizeof (info), 829 &cbReturned, 830 NULL)) 831 rc = info.result; 832 else 833 rc = VERR_FILE_IO_ERROR; 834 if (RT_SUCCESS(rc)) 835 *pu32ClientID = info.u32ClientID; 836 return rc; 837 } 838 839 840 /** Set a 32bit unsigned integer parameter to an HGCM request */ 841 static void VbglHGCMParmUInt32Set(HGCMFunctionParameter *pParm, uint32_t u32) 842 { 843 pParm->type = VMMDevHGCMParmType_32bit; 844 pParm->u.value64 = 0; /* init unused bits to 0 */ 845 pParm->u.value32 = u32; 846 } 847 848 849 /** Get a 32bit unsigned integer returned from an HGCM request */ 850 static int VbglHGCMParmUInt32Get(HGCMFunctionParameter *pParm, uint32_t *pu32) 851 { 852 if (pParm->type == VMMDevHGCMParmType_32bit) 853 { 854 *pu32 = pParm->u.value32; 855 return VINF_SUCCESS; 856 } 857 return VERR_INVALID_PARAMETER; 858 } 859 860 861 /** Set a pointer parameter to an HGCM request */ 862 static void VbglHGCMParmPtrSet(HGCMFunctionParameter *pParm, void *pv, uint32_t cb) 863 { 864 pParm->type = VMMDevHGCMParmType_LinAddr; 865 pParm->u.Pointer.size = cb; 866 pParm->u.Pointer.u.linearAddr = (uintptr_t)pv; 867 } 868 869 870 /** Make an HGCM call */ 871 static int hgcmCall(HANDLE hDevice, VBoxGuestHGCMCallInfo *pMsg, size_t cbMsg) 872 { 873 DWORD cbReturned; 874 int rc = VERR_NOT_SUPPORTED; 875 876 if (DeviceIoControl (hDevice, 877 IOCTL_VBOXGUEST_HGCM_CALL, 878 pMsg, cbMsg, 879 pMsg, cbMsg, 880 &cbReturned, 881 NULL)) 882 rc = VINF_SUCCESS; 883 return rc; 884 } 885 886 887 /** 888 * Retrieve a property from the host/guest configuration registry 889 * @returns IPRT status code 890 * @param hDevice handle to the VBox device 891 * @param u32ClientID The client id returned by VbglR3ClipboardConnect(). 892 * @param pszKey The registry key to save to. 893 * @param pszValue Where to store the value retrieved. 894 * @param cbValue The size of the buffer pszValue points to. 895 * @param pcbActual Where to store the required buffer size on 896 * overflow or the value size on success. A value 897 * of zero means that the property does not exist. 898 * Optional. 899 */ 900 static int hgcmInfoSvcGetProp(HANDLE hDevice, uint32_t u32ClientID, 901 char *pszKey, char *pszValue, 902 uint32_t cbValue, uint32_t *pcbActual) 903 { 904 using namespace svcInfo; 905 906 if (!VALID_PTR(pszValue)) 907 return VERR_INVALID_POINTER; 908 GetConfigKey Msg; 909 910 Msg.hdr.result = (uint32_t)VERR_WRONG_ORDER; /** @todo drop the cast when the result type has been fixed! */ 911 Msg.hdr.u32ClientID = u32ClientID; 912 Msg.hdr.u32Function = GET_CONFIG_KEY; 913 Msg.hdr.cParms = 3; 914 VbglHGCMParmPtrSet(&Msg.key, pszKey, strlen(pszKey) + 1); 915 VbglHGCMParmPtrSet(&Msg.value, pszValue, cbValue); 916 VbglHGCMParmUInt32Set(&Msg.size, 0); 917 int rc = hgcmCall(hDevice, &Msg.hdr, sizeof(Msg)); 918 if (RT_SUCCESS(rc)) 919 rc = Msg.hdr.result; 920 uint32_t cbActual; 921 if (RT_SUCCESS(rc)) 922 rc = VbglHGCMParmUInt32Get(&Msg.size, &cbActual); 923 if (RT_SUCCESS(rc)) 924 { 925 if (pcbActual != NULL) 926 *pcbActual = cbActual; 927 if (cbActual > cbValue) 928 rc = VINF_BUFFER_OVERFLOW; 929 else 930 rc = Msg.hdr.result; 931 if ((cbValue > 0) && (0 == cbActual)) /* No such property */ 932 pszValue[0] = 0; 933 934 } 935 return rc; 936 } 937 938 939 /** 940 * Store a property from the host/guest configuration registry 941 * @returns IPRT status code 942 * @param hDevice handle to the VBox device 943 * @param u32ClientID The client id returned by VbglR3ClipboardConnect(). 944 * @param pszKey The registry key to save to. 945 * @param pszValue The value to store. If this is NULL then the key 946 * will be removed. 947 */ 948 static int hgcmInfoSvcSetProp(HANDLE hDevice, uint32_t u32ClientID, 949 char *pszKey, char *pszValue) 950 { 951 using namespace svcInfo; 952 953 if (!VALID_PTR(pszKey)) 954 return VERR_INVALID_POINTER; 955 if (!VALID_PTR(pszValue) && (pszValue != NULL)); 956 int rc; 957 958 if (pszValue != NULL) 959 { 960 SetConfigKey Msg; 961 962 Msg.hdr.result = (uint32_t)VERR_WRONG_ORDER; /** @todo drop the cast when the result type has been fixed! */ 963 Msg.hdr.u32ClientID = u32ClientID; 964 Msg.hdr.u32Function = SET_CONFIG_KEY; 965 Msg.hdr.cParms = 2; 966 VbglHGCMParmPtrSet(&Msg.key, pszKey, strlen(pszKey) + 1); 967 VbglHGCMParmPtrSet(&Msg.value, pszValue, strlen(pszValue) + 1); 968 rc = hgcmCall(hDevice, &Msg.hdr, sizeof(Msg)); 969 if (RT_SUCCESS(rc)) 970 rc = Msg.hdr.result; 971 } 972 else 973 { 974 DelConfigKey Msg; 975 976 Msg.hdr.result = (uint32_t)VERR_WRONG_ORDER; /** @todo drop the cast when the result type has been fixed! */ 977 Msg.hdr.u32ClientID = u32ClientID; 978 Msg.hdr.u32Function = DEL_CONFIG_KEY; 979 Msg.hdr.cParms = 1; 980 VbglHGCMParmPtrSet(&Msg.key, pszKey, strlen(pszKey) + 1); 981 rc = hgcmCall(hDevice, &Msg.hdr, sizeof(Msg)); 982 if (RT_SUCCESS(rc)) 983 rc = Msg.hdr.result; 984 } 985 return rc; 986 } 987 988 989 /** Disconnects from an HGCM service. */ 990 static void hgcmDisconnect(HANDLE hDevice, uint32_t u32ClientID) 991 { 992 if (u32ClientID == 0) 993 return; 994 995 VBoxGuestHGCMDisconnectInfo info; 996 memset (&info, 0, sizeof (info)); 997 info.u32ClientID = u32ClientID; 998 999 DWORD cbReturned; 1000 DeviceIoControl (hDevice, 1001 IOCTL_VBOXGUEST_HGCM_DISCONNECT, 1002 &info, sizeof (info), 1003 &info, sizeof (info), 1004 &cbReturned, 1005 NULL); 1006 } 1007 1008 1009 /** 1010 * Retrieves a value from the host/guest configuration registry. 1011 * This is accessed through the "VBoxSharedInfoSvc" HGCM service. 1012 * 1013 * @returns IPRT status value 1014 * @param key (string) the key which the value is stored under. 1015 */ 1016 static int handleGetGuestProperty(int argc, char *argv[]) 1017 { 1018 if (argc != 1) 1019 { 1020 printHelp(); 1021 return 1; 1022 } 1023 char szValue[svcInfo::KEY_MAX_VALUE_LEN]; 1024 HANDLE hDevice = INVALID_HANDLE_VALUE; 1025 uint32_t u32ClientID = 0; 1026 int rc = openGuestDevice(&hDevice); 1027 if (!RT_SUCCESS(rc)) 1028 printf("Failed to open the VirtualBox device, RT error %d\n", rc); 1029 if (RT_SUCCESS(rc)) 1030 { 1031 rc = hgcmConnect(hDevice, "VBoxSharedInfoSvc", &u32ClientID); 1032 if (!RT_SUCCESS(rc)) 1033 printf("Failed to connect to the host/guest registry service, RT error %d\n", rc); 1034 } 1035 if (RT_SUCCESS(rc)) 1036 { 1037 rc = hgcmInfoSvcGetProp(hDevice, u32ClientID, argv[0], szValue, 1038 sizeof(szValue), NULL); 1039 if (!RT_SUCCESS(rc)) 1040 printf("Failed to retrieve the property value, RT error %d\n", rc); 1041 } 1042 if (RT_SUCCESS(rc)) 1043 { 1044 if (strlen(szValue) > 0) 1045 printf("Value: %s\n", szValue); 1046 else 1047 printf("No value set!\n"); 1048 } 1049 if (u32ClientID != 0) 1050 hgcmDisconnect(hDevice, u32ClientID); 1051 if (hDevice != INVALID_HANDLE_VALUE) 1052 CloseHandle(hDevice); 1053 return rc; 1054 } 1055 1056 1057 /** 1058 * Writes a value to the host/guest configuration registry. 1059 * This is accessed through the "VBoxSharedInfoSvc" HGCM service. 1060 * 1061 * @returns IPRT status value 1062 * @param key (string) the key which the value is stored under. 1063 * @param value (string) the value to write. If empty, the key will be 1064 * removed. 1065 */ 1066 static int handleSetGuestProperty(int argc, char *argv[]) 1067 { 1068 if (argc != 1 && argc != 2) 1069 { 1070 printHelp(); 1071 return 1; 1072 } 1073 HANDLE hDevice = INVALID_HANDLE_VALUE; 1074 char *pszValue = NULL; 1075 if (2 == argc) 1076 pszValue = argv[1]; 1077 uint32_t u32ClientID = 0; 1078 int rc = openGuestDevice(&hDevice); 1079 if (!RT_SUCCESS(rc)) 1080 printf("Failed to open the VirtualBox device, RT error %d\n", rc); 1081 if (RT_SUCCESS(rc)) 1082 { 1083 rc = hgcmConnect(hDevice, "VBoxSharedInfoSvc", &u32ClientID); 1084 if (!RT_SUCCESS(rc)) 1085 printf("Failed to connect to the host/guest registry service, RT error %d\n", rc); 1086 } 1087 if (RT_SUCCESS(rc)) 1088 { 1089 rc = hgcmInfoSvcSetProp(hDevice, u32ClientID, argv[0], pszValue); 1090 if (!RT_SUCCESS(rc)) 1091 printf("Failed to store the property value, RT error %d\n", rc); 1092 } 1093 if (u32ClientID != 0) 1094 hgcmDisconnect(hDevice, u32ClientID); 1095 if (hDevice != INVALID_HANDLE_VALUE) 1096 CloseHandle(hDevice); 1097 return rc; 1098 } 1099 1100 1101 /** 781 1102 * Main function 782 1103 */ … … 823 1144 handleSetVideoMode(argc - 2, &argv[2]); 824 1145 } 1146 else if (stricmp(argv[1], "getguestproperty") == 0) 1147 { 1148 int rc = handleGetGuestProperty(argc - 2, &argv[2]); 1149 return RT_SUCCESS(rc) ? 0 : 1; 1150 } 1151 else if (stricmp(argv[1], "setguestproperty") == 0) 1152 { 1153 handleSetGuestProperty(argc - 2, &argv[2]); 1154 } 825 1155 else 826 1156 {
Note:
See TracChangeset
for help on using the changeset viewer.