Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygenksproxy.cpp
Go to the documentation of this file.
00001 /* 00002 * COPYRIGHT: See COPYING in the top level directory 00003 * PROJECT: ReactOS WDM Streaming ActiveMovie Proxy 00004 * FILE: dll/directx/ksproxy/ksproxy.c 00005 * PURPOSE: ActiveMovie Proxy functions 00006 * 00007 * PROGRAMMERS: Dmitry Chapyshev 00008 Johannes Anderwald (janderwald@reactos.org) 00009 */ 00010 00011 #include "precomp.h" 00012 00013 00014 const GUID CLSID_KsClockForwarder = {0x877e4351, 0x6fea, 0x11d0, {0xb8, 0x63, 0x00, 0xaa, 0x00, 0xa2, 0x16, 0xa1}}; 00015 const GUID CLSID_KsQualityForwarder = {0xe05592e4, 0xc0b5, 0x11d0, {0xa4, 0x39, 0x00, 0xa0, 0xc9, 0x22, 0x31, 0x96}}; 00016 00017 00018 #ifndef _MSC_VER 00019 const GUID CLSID_KsIBasicAudioInterfaceHandler = {0xb9f8ac3e, 0x0f71, 0x11d2, {0xb7, 0x2c, 0x00, 0xc0, 0x4f, 0xb6, 0xbd, 0x3d}}; 00020 const GUID KSPROPSETID_Pin = {0x8C134960, 0x51AD, 0x11CF, {0x87, 0x8A, 0x94, 0xF8, 0x01, 0xC1, 0x00, 0x00}}; 00021 const GUID KSINTERFACESETID_Standard = {STATIC_KSINTERFACESETID_Standard}; 00022 const GUID CLSID_Proxy = {0x17CCA71B, 0xECD7, 0x11D0, {0xB9, 0x08, 0x00, 0xA0, 0xC9, 0x22, 0x31, 0x96}}; 00023 #endif 00024 00025 static INTERFACE_TABLE InterfaceTable[] = 00026 { 00027 {&MEDIATYPE_Audio, CKsDataTypeHandler_Constructor}, 00028 {&KSINTERFACESETID_Standard, CKsInterfaceHandler_Constructor}, 00029 {&CLSID_KsClockForwarder, CKsClockForwarder_Constructor}, 00030 {&CLSID_KsQualityForwarder, CKsQualityForwarder_Constructor}, 00031 {&IID_IVPConfig, CVPConfig_Constructor}, 00032 {&IID_IVPVBIConfig, CVPVBIConfig_Constructor}, 00033 {&CLSID_KsIBasicAudioInterfaceHandler, CKsBasicAudio_Constructor}, 00034 {&CLSID_Proxy, CKsProxy_Constructor}, 00035 {NULL, NULL} 00036 }; 00037 00038 KSDDKAPI 00039 HRESULT 00040 WINAPI 00041 KsSynchronousDeviceControl( 00042 HANDLE Handle, 00043 ULONG IoControl, 00044 PVOID InBuffer, 00045 ULONG InLength, 00046 PVOID OutBuffer, 00047 ULONG OutLength, 00048 PULONG BytesReturned) 00049 { 00050 OVERLAPPED Overlapped; 00051 DWORD Transferred; 00052 00053 /* zero overlapped */ 00054 RtlZeroMemory(&Overlapped, sizeof(OVERLAPPED)); 00055 00056 /* create notification event */ 00057 Overlapped.hEvent = CreateEventW(NULL, TRUE, FALSE, NULL); 00058 00059 if (!Overlapped.hEvent) 00060 { 00061 /* failed */ 00062 return MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIN32, GetLastError()); 00063 } 00064 00065 if (!DeviceIoControl(Handle, IoControl, InBuffer, InLength, OutBuffer, OutLength, BytesReturned, &Overlapped)) 00066 { 00067 /* operation failed */ 00068 if (GetLastError() != ERROR_IO_PENDING) 00069 { 00070 /* failed */ 00071 CloseHandle(Overlapped.hEvent); 00072 return MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIN32, GetLastError()); 00073 } 00074 } 00075 00076 /* get result of pending operation */ 00077 if (!GetOverlappedResult(Handle, &Overlapped, &Transferred, TRUE)) 00078 { 00079 /* failed */ 00080 CloseHandle(Overlapped.hEvent); 00081 return MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIN32, GetLastError()); 00082 } 00083 00084 /* store number of bytes transferred */ 00085 *BytesReturned = Transferred; 00086 00087 /* close event object */ 00088 CloseHandle(Overlapped.hEvent); 00089 00090 /* done */ 00091 return NOERROR; 00092 } 00093 00094 KSDDKAPI 00095 HRESULT 00096 WINAPI 00097 KsResolveRequiredAttributes( 00098 PKSDATARANGE DataRange, 00099 KSMULTIPLE_ITEM *Attributes OPTIONAL) 00100 { 00101 //UNIMPLEMENTED 00102 return NOERROR; 00103 } 00104 00105 KSDDKAPI 00106 HRESULT 00107 WINAPI 00108 KsOpenDefaultDevice( 00109 REFGUID Category, 00110 ACCESS_MASK Access, 00111 PHANDLE DeviceHandle) 00112 { 00113 HDEVINFO hList; 00114 SP_DEVICE_INTERFACE_DATA DeviceInterfaceData; 00115 PSP_DEVICE_INTERFACE_DETAIL_DATA_W DeviceInterfaceDetailData; 00116 WCHAR Path[MAX_PATH+sizeof(SP_DEVICE_INTERFACE_DETAIL_DATA_W)]; 00117 00118 /* open device list */ 00119 hList = SetupDiGetClassDevsW(&Category, NULL, NULL, DIGCF_DEVICEINTERFACE | DIGCF_PRESENT); 00120 00121 if (hList == INVALID_HANDLE_VALUE) 00122 { 00123 /* failed */ 00124 return MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIN32, GetLastError()); 00125 } 00126 00127 /* setup parameters */ 00128 DeviceInterfaceData.cbSize = sizeof(SP_DEVICE_INTERFACE_DATA); 00129 00130 if (SetupDiEnumDeviceInterfaces(hList, NULL, &Category, 0, &DeviceInterfaceData)) 00131 { 00132 /* setup interface data struct */ 00133 DeviceInterfaceDetailData = (PSP_DEVICE_INTERFACE_DETAIL_DATA_W)Path; 00134 DeviceInterfaceDetailData->cbSize = sizeof(SP_DEVICE_INTERFACE_DETAIL_DATA_W); 00135 00136 /* get device interface details */ 00137 if (SetupDiGetDeviceInterfaceDetailW(hList, &DeviceInterfaceData, DeviceInterfaceDetailData, sizeof(Path), NULL, NULL)) 00138 { 00139 /* open device */ 00140 *DeviceHandle = CreateFileW(DeviceInterfaceDetailData->DevicePath, GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, FILE_FLAG_OVERLAPPED | FILE_ATTRIBUTE_NORMAL, NULL); 00141 00142 if (*DeviceHandle != INVALID_HANDLE_VALUE) 00143 { 00144 /* operation succeeded */ 00145 SetupDiDestroyDeviceInfoList(hList); 00146 return NOERROR; 00147 } 00148 } 00149 } 00150 00151 /* free device list */ 00152 SetupDiDestroyDeviceInfoList(hList); 00153 00154 /* failed */ 00155 return MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIN32, GetLastError()); 00156 } 00157 00158 KSDDKAPI 00159 HRESULT 00160 WINAPI 00161 KsGetMultiplePinFactoryItems( 00162 HANDLE FilterHandle, 00163 ULONG PinFactoryId, 00164 ULONG PropertyId, 00165 PVOID *Items) 00166 { 00167 KSP_PIN Property; 00168 ULONG BytesReturned, NumData; 00169 HRESULT hResult; 00170 00171 /* zero pin property */ 00172 RtlZeroMemory(&Property, sizeof(KSP_PIN)); 00173 Property.Property.Set = KSPROPSETID_Pin; 00174 Property.Property.Id = PropertyId; 00175 Property.Property.Flags = KSPROPERTY_TYPE_GET; 00176 Property.PinId = PinFactoryId; 00177 00178 /* query pin factory */ 00179 hResult = KsSynchronousDeviceControl(FilterHandle, IOCTL_KS_PROPERTY, (PVOID)&Property, sizeof(KSP_PIN), NULL, 0, &BytesReturned); 00180 00181 if (hResult == MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIN32, ERROR_INSUFFICIENT_BUFFER)) 00182 { 00183 /* buffer too small */ 00184 hResult = KsSynchronousDeviceControl(FilterHandle, IOCTL_KS_PROPERTY, (PVOID)&Property, sizeof(KSP_PIN), (PVOID)&NumData, sizeof(ULONG), &BytesReturned); 00185 00186 if (SUCCEEDED(hResult)) 00187 { 00188 /* store required data size */ 00189 BytesReturned = NumData; 00190 hResult = MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIN32, ERROR_MORE_DATA); 00191 } 00192 } 00193 00194 if (hResult == MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIN32, ERROR_MORE_DATA)) 00195 { 00196 /* allocate data */ 00197 *Items = CoTaskMemAlloc(BytesReturned); 00198 00199 if (!*Items) 00200 { 00201 /* no memory */ 00202 return E_OUTOFMEMORY; 00203 } 00204 00205 /* retry querying property */ 00206 hResult = KsSynchronousDeviceControl(FilterHandle, IOCTL_KS_PROPERTY, (PVOID)&Property, sizeof(KSP_PIN), (PVOID)*Items, BytesReturned, &BytesReturned); 00207 00208 /* check for success */ 00209 if (FAILED(hResult)) 00210 { 00211 /* free memory */ 00212 CoTaskMemFree(*Items); 00213 } 00214 } 00215 00216 /* done */ 00217 return hResult; 00218 } 00219 00220 KSDDKAPI 00221 HRESULT 00222 WINAPI 00223 KsGetMediaTypeCount( 00224 HANDLE FilterHandle, 00225 ULONG PinFactoryId, 00226 ULONG *MediaTypeCount) 00227 { 00228 PKSMULTIPLE_ITEM MultipleItem; 00229 HRESULT hr; 00230 00231 /* try get contrained data ranges */ 00232 hr = KsGetMultiplePinFactoryItems(FilterHandle, PinFactoryId, KSPROPERTY_PIN_CONSTRAINEDDATARANGES, (PVOID*)&MultipleItem); 00233 00234 /* check for failure*/ 00235 if (FAILED(hr)) 00236 { 00237 /* try getting default data ranges */ 00238 hr = KsGetMultiplePinFactoryItems(FilterHandle, PinFactoryId, KSPROPERTY_PIN_DATARANGES, (PVOID*)&MultipleItem); 00239 } 00240 00241 if (SUCCEEDED(hr)) 00242 { 00243 /* store number of media types */ 00244 *MediaTypeCount = MultipleItem->Count; 00245 00246 /* free memory */ 00247 CoTaskMemFree(MultipleItem); 00248 } 00249 00250 /* done */ 00251 return hr; 00252 } 00253 00254 KSDDKAPI 00255 HRESULT 00256 WINAPI 00257 KsGetMediaType( 00258 int Position, 00259 AM_MEDIA_TYPE *AmMediaType, 00260 HANDLE FilterHandle, 00261 ULONG PinFactoryId) 00262 { 00263 HRESULT hr; 00264 PKSMULTIPLE_ITEM ItemList; 00265 int i = 0; 00266 PKSDATAFORMAT DataFormat; 00267 00268 if (Position < 0) 00269 return E_INVALIDARG; 00270 00271 // get current supported ranges 00272 hr = KsGetMultiplePinFactoryItems(FilterHandle, PinFactoryId, KSPROPERTY_PIN_CONSTRAINEDDATARANGES, (PVOID*)&ItemList); 00273 if (FAILED(hr)) 00274 { 00275 // get standard dataranges 00276 hr = KsGetMultiplePinFactoryItems(FilterHandle, PinFactoryId, KSPROPERTY_PIN_DATARANGES, (PVOID*)&ItemList); 00277 00278 //check for success 00279 if (FAILED(hr)) 00280 return hr; 00281 } 00282 00283 if ((ULONG)Position >= ItemList->Count) 00284 { 00285 // out of bounds 00286 CoTaskMemFree(ItemList); 00287 return MAKE_HRESULT(SEVERITY_ERROR, FACILITY_WIN32, ERROR_NO_MORE_ITEMS); 00288 } 00289 00290 // goto first datarange 00291 DataFormat = (PKSDATAFORMAT)(ItemList + 1); 00292 00293 while(i != Position) 00294 { 00295 // goto next format; 00296 DataFormat = (PKSDATAFORMAT)(ULONG_PTR)(DataFormat + DataFormat->FormatSize); 00297 i++; 00298 } 00299 00300 00301 DataFormat->FormatSize -= sizeof(KSDATAFORMAT); 00302 if (DataFormat->FormatSize) 00303 { 00304 // copy extra format buffer 00305 AmMediaType->pbFormat = (BYTE*)CoTaskMemAlloc(DataFormat->FormatSize); 00306 if (!AmMediaType->pbFormat) 00307 { 00308 // not enough memory 00309 CoTaskMemFree(ItemList); 00310 return E_OUTOFMEMORY; 00311 } 00312 // copy format buffer 00313 CopyMemory(AmMediaType->pbFormat, (DataFormat + 1), DataFormat->FormatSize); 00314 AmMediaType->cbFormat = DataFormat->FormatSize; 00315 } 00316 else 00317 { 00318 // no format buffer 00319 AmMediaType->pbFormat = NULL; 00320 AmMediaType->cbFormat = 0; 00321 } 00322 00323 // copy type info 00324 CopyMemory(&AmMediaType->majortype, &DataFormat->MajorFormat, sizeof(GUID)); 00325 CopyMemory(&AmMediaType->subtype, &DataFormat->SubFormat, sizeof(GUID)); 00326 CopyMemory(&AmMediaType->formattype, &DataFormat->Specifier, sizeof(GUID)); 00327 AmMediaType->bTemporalCompression = FALSE; //FIXME verify 00328 AmMediaType->pUnk = NULL; //FIXME 00329 AmMediaType->lSampleSize = DataFormat->SampleSize; 00330 AmMediaType->bFixedSizeSamples = (AmMediaType->lSampleSize) ? TRUE : FALSE; 00331 00332 // free dataformat list 00333 CoTaskMemFree(ItemList); 00334 00335 return NOERROR; 00336 } 00337 00338 extern "C" 00339 KSDDKAPI 00340 HRESULT 00341 WINAPI 00342 DllUnregisterServer(void) 00343 { 00344 ULONG Index = 0; 00345 LPOLESTR pStr; 00346 HRESULT hr = S_OK; 00347 HKEY hClass; 00348 00349 if (RegOpenKeyExW(HKEY_CLASSES_ROOT, L"CLSID", 0, KEY_SET_VALUE, &hClass) != ERROR_SUCCESS) 00350 return E_FAIL; 00351 00352 do 00353 { 00354 hr = StringFromCLSID(*InterfaceTable[Index].riid, &pStr); 00355 if (FAILED(hr)) 00356 break; 00357 00358 RegDeleteKeyW(hClass, pStr); 00359 CoTaskMemFree(pStr); 00360 Index++; 00361 }while(InterfaceTable[Index].lpfnCI != 0); 00362 00363 RegCloseKey(hClass); 00364 return hr; 00365 } 00366 00367 extern "C" 00368 KSDDKAPI 00369 HRESULT 00370 WINAPI 00371 DllRegisterServer(void) 00372 { 00373 ULONG Index = 0; 00374 LPOLESTR pStr; 00375 HRESULT hr = S_OK; 00376 HKEY hClass, hKey, hSubKey; 00377 static LPCWSTR ModuleName = L"ksproxy.ax"; 00378 static LPCWSTR ThreadingModel = L"Both"; 00379 00380 if (RegOpenKeyExW(HKEY_CLASSES_ROOT, L"CLSID", 0, KEY_WRITE, &hClass) != ERROR_SUCCESS) 00381 return E_FAIL; 00382 00383 do 00384 { 00385 hr = StringFromCLSID(*InterfaceTable[Index].riid, &pStr); 00386 if (FAILED(hr)) 00387 break; 00388 00389 if (RegCreateKeyExW(hClass, pStr, 0, 0, 0, KEY_WRITE, NULL, &hKey, 0) == ERROR_SUCCESS) 00390 { 00391 if (RegCreateKeyExW(hKey, L"InprocServer32", 0, 0, 0, KEY_WRITE, NULL, &hSubKey, 0) == ERROR_SUCCESS) 00392 { 00393 RegSetValueExW(hSubKey, 0, 0, REG_SZ, (const BYTE*)ModuleName, (wcslen(ModuleName) + 1) * sizeof(WCHAR)); 00394 RegSetValueExW(hSubKey, L"ThreadingModel", 0, REG_SZ, (const BYTE*)ThreadingModel, (wcslen(ThreadingModel) + 1) * sizeof(WCHAR)); 00395 RegCloseKey(hSubKey); 00396 } 00397 RegCloseKey(hKey); 00398 } 00399 00400 CoTaskMemFree(pStr); 00401 Index++; 00402 }while(InterfaceTable[Index].lpfnCI != 0); 00403 00404 RegCloseKey(hClass); 00405 return hr; 00406 } 00407 00408 KSDDKAPI 00409 HRESULT 00410 WINAPI 00411 DllGetClassObject( 00412 REFCLSID rclsid, 00413 REFIID riid, 00414 LPVOID *ppv) 00415 { 00416 UINT i; 00417 HRESULT hres = E_OUTOFMEMORY; 00418 IClassFactory * pcf = NULL; 00419 00420 if (!ppv) 00421 return E_INVALIDARG; 00422 00423 *ppv = NULL; 00424 00425 for (i = 0; InterfaceTable[i].riid; i++) 00426 { 00427 if (IsEqualIID(*InterfaceTable[i].riid, rclsid)) 00428 { 00429 pcf = CClassFactory_fnConstructor(InterfaceTable[i].lpfnCI, NULL, NULL); 00430 break; 00431 } 00432 } 00433 00434 if (!pcf) 00435 { 00436 return CLASS_E_CLASSNOTAVAILABLE; 00437 } 00438 00439 hres = pcf->QueryInterface(riid, ppv); 00440 pcf->Release(); 00441 00442 return hres; 00443 } 00444 00445 KSDDKAPI 00446 HRESULT 00447 WINAPI 00448 DllCanUnloadNow(void) 00449 { 00450 return S_OK; 00451 } 00452 Generated on Thu May 24 2012 04:21:59 for ReactOS by
1.7.6.1
|