1 /* 2 * IParseDisplayName implementation for DEVENUM.dll 3 * 4 * Copyright (C) 2002 Robert Shearman 5 * 6 * This library is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU Lesser General Public 8 * License as published by the Free Software Foundation; either 9 * version 2.1 of the License, or (at your option) any later version. 10 * 11 * This library is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14 * Lesser General Public License for more details. 15 * 16 * You should have received a copy of the GNU Lesser General Public 17 * License along with this library; if not, write to the Free Software 18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA 19 * 20 * NOTES ON THIS FILE: 21 * - Implements IParseDisplayName interface which creates a moniker 22 * from a string in a special format 23 */ 24 #include "devenum_private.h" 25 26 #include "wine/debug.h" 27 28 WINE_DEFAULT_DEBUG_CHANNEL(devenum); 29 30 static HRESULT WINAPI DEVENUM_IParseDisplayName_QueryInterface(IParseDisplayName *iface, 31 REFIID riid, void **ppv) 32 { 33 TRACE("\n\tIID:\t%s\n",debugstr_guid(riid)); 34 35 if (!ppv) 36 return E_POINTER; 37 38 if (IsEqualGUID(riid, &IID_IUnknown) || 39 IsEqualGUID(riid, &IID_IParseDisplayName)) 40 { 41 *ppv = iface; 42 IParseDisplayName_AddRef(iface); 43 return S_OK; 44 } 45 46 FIXME("- no interface IID: %s\n", debugstr_guid(riid)); 47 *ppv = NULL; 48 return E_NOINTERFACE; 49 } 50 51 static ULONG WINAPI DEVENUM_IParseDisplayName_AddRef(IParseDisplayName *iface) 52 { 53 TRACE("\n"); 54 55 DEVENUM_LockModule(); 56 57 return 2; /* non-heap based object */ 58 } 59 60 static ULONG WINAPI DEVENUM_IParseDisplayName_Release(IParseDisplayName *iface) 61 { 62 TRACE("\n"); 63 64 DEVENUM_UnlockModule(); 65 66 return 1; /* non-heap based object */ 67 } 68 69 /********************************************************************** 70 * DEVENUM_IParseDisplayName_ParseDisplayName 71 * 72 * Creates a moniker referenced to by the display string argument 73 * 74 * POSSIBLE BUGS: 75 * Might not handle more complicated strings properly (ie anything 76 * not in "@device:sw:{CLSID1}\<filter name or CLSID>" format 77 */ 78 static HRESULT WINAPI DEVENUM_IParseDisplayName_ParseDisplayName(IParseDisplayName *iface, 79 IBindCtx *pbc, LPOLESTR name, ULONG *eaten, IMoniker **ret) 80 { 81 WCHAR buffer[MAX_PATH]; 82 enum device_type type; 83 MediaCatMoniker *mon; 84 CLSID class; 85 86 TRACE("(%p, %s, %p, %p)\n", pbc, debugstr_w(name), eaten, ret); 87 88 *ret = NULL; 89 if (eaten) 90 *eaten = lstrlenW(name); 91 92 name = wcschr(name, ':') + 1; 93 94 if (!wcsncmp(name, swW, 3)) 95 { 96 type = DEVICE_FILTER; 97 name += 3; 98 } 99 else if (!wcsncmp(name, cmW, 3)) 100 { 101 type = DEVICE_CODEC; 102 name += 3; 103 } 104 else if (!wcsncmp(name, dmoW, 4)) 105 { 106 type = DEVICE_DMO; 107 name += 4; 108 } 109 else 110 { 111 FIXME("unhandled device type %s\n", debugstr_w(name)); 112 return MK_E_SYNTAX; 113 } 114 115 if (!(mon = DEVENUM_IMediaCatMoniker_Construct())) 116 return E_OUTOFMEMORY; 117 118 if (type == DEVICE_DMO) 119 { 120 lstrcpynW(buffer, name, CHARS_IN_GUID); 121 if (FAILED(CLSIDFromString(buffer, &mon->clsid))) 122 { 123 IMoniker_Release(&mon->IMoniker_iface); 124 return MK_E_SYNTAX; 125 } 126 127 lstrcpynW(buffer, name + CHARS_IN_GUID - 1, CHARS_IN_GUID); 128 if (FAILED(CLSIDFromString(buffer, &mon->class))) 129 { 130 IMoniker_Release(&mon->IMoniker_iface); 131 return MK_E_SYNTAX; 132 } 133 } 134 else 135 { 136 lstrcpynW(buffer, name, CHARS_IN_GUID); 137 if (CLSIDFromString(buffer, &class) == S_OK) 138 { 139 mon->has_class = TRUE; 140 mon->class = class; 141 name += CHARS_IN_GUID; 142 } 143 144 if (!(mon->name = CoTaskMemAlloc((lstrlenW(name) + 1) * sizeof(WCHAR)))) 145 { 146 IMoniker_Release(&mon->IMoniker_iface); 147 return E_OUTOFMEMORY; 148 } 149 lstrcpyW(mon->name, name); 150 } 151 152 mon->type = type; 153 154 *ret = &mon->IMoniker_iface; 155 156 return S_OK; 157 } 158 159 /********************************************************************** 160 * IParseDisplayName_Vtbl 161 */ 162 static const IParseDisplayNameVtbl IParseDisplayName_Vtbl = 163 { 164 DEVENUM_IParseDisplayName_QueryInterface, 165 DEVENUM_IParseDisplayName_AddRef, 166 DEVENUM_IParseDisplayName_Release, 167 DEVENUM_IParseDisplayName_ParseDisplayName 168 }; 169 170 /* The one instance of this class */ 171 IParseDisplayName DEVENUM_ParseDisplayName = { &IParseDisplayName_Vtbl }; 172