ReactOS Fundraising Campaign 2012
 
€ 4,410 / € 30,000

Information | Donate

Home | Info | Community | Development | myReactOS | Contact Us

  1. Home
  2. Community
  3. Development
  4. myReactOS
  5. Fundraiser 2012

  1. Main Page
  2. Alphabetical List
  3. Data Structures
  4. Directories
  5. File List
  6. Data Fields
  7. Globals
  8. Related Pages

ReactOS Development > Doxygen

asmname.c
Go to the documentation of this file.
00001 /*
00002  * IAssemblyName implementation
00003  *
00004  * Copyright 2008 James Hawkins
00005  *
00006  * This library is free software; you can redistribute it and/or
00007  * modify it under the terms of the GNU Lesser General Public
00008  * License as published by the Free Software Foundation; either
00009  * version 2.1 of the License, or (at your option) any later version.
00010  *
00011  * This library is distributed in the hope that it will be useful,
00012  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00013  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00014  * Lesser General Public License for more details.
00015  *
00016  * You should have received a copy of the GNU Lesser General Public
00017  * License along with this library; if not, write to the Free Software
00018  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
00019  */
00020 
00021 #include <stdarg.h>
00022 #include <assert.h>
00023 
00024 #define COBJMACROS
00025 #define INITGUID
00026 
00027 #include "windef.h"
00028 #include "winbase.h"
00029 #include "winuser.h"
00030 #include "ole2.h"
00031 #include "guiddef.h"
00032 #include "fusion.h"
00033 #include "corerror.h"
00034 
00035 #include "wine/debug.h"
00036 #include "wine/unicode.h"
00037 #include "fusionpriv.h"
00038 
00039 WINE_DEFAULT_DEBUG_CHANNEL(fusion);
00040 
00041 typedef struct {
00042     IAssemblyName IAssemblyName_iface;
00043 
00044     LPWSTR path;
00045 
00046     LPWSTR displayname;
00047     LPWSTR name;
00048     LPWSTR culture;
00049     LPWSTR procarch;
00050 
00051     WORD version[4];
00052     DWORD versize;
00053 
00054     BYTE pubkey[8];
00055     BOOL haspubkey;
00056 
00057     LONG ref;
00058 } IAssemblyNameImpl;
00059 
00060 static const WCHAR separator[] = {',',' ',0};
00061 static const WCHAR version[] = {'V','e','r','s','i','o','n',0};
00062 static const WCHAR culture[] = {'C','u','l','t','u','r','e',0};
00063 static const WCHAR pubkey[] =
00064     {'P','u','b','l','i','c','K','e','y','T','o','k','e','n',0};
00065 static const WCHAR procarch[] = {'p','r','o','c','e','s','s','o','r',
00066     'A','r','c','h','i','t','e','c','t','u','r','e',0};
00067 
00068 #define CHARS_PER_PUBKEY 16
00069 
00070 static inline IAssemblyNameImpl *impl_from_IAssemblyName(IAssemblyName *iface)
00071 {
00072     return CONTAINING_RECORD(iface, IAssemblyNameImpl, IAssemblyName_iface);
00073 }
00074 
00075 static HRESULT WINAPI IAssemblyNameImpl_QueryInterface(IAssemblyName *iface,
00076                                                        REFIID riid, LPVOID *ppobj)
00077 {
00078     IAssemblyNameImpl *This = impl_from_IAssemblyName(iface);
00079 
00080     TRACE("(%p, %s, %p)\n", This, debugstr_guid(riid), ppobj);
00081 
00082     *ppobj = NULL;
00083 
00084     if (IsEqualIID(riid, &IID_IUnknown) ||
00085         IsEqualIID(riid, &IID_IAssemblyName))
00086     {
00087         IUnknown_AddRef(iface);
00088         *ppobj = This;
00089         return S_OK;
00090     }
00091 
00092     WARN("(%p, %s, %p): not found\n", This, debugstr_guid(riid), ppobj);
00093     return E_NOINTERFACE;
00094 }
00095 
00096 static ULONG WINAPI IAssemblyNameImpl_AddRef(IAssemblyName *iface)
00097 {
00098     IAssemblyNameImpl *This = impl_from_IAssemblyName(iface);
00099     ULONG refCount = InterlockedIncrement(&This->ref);
00100 
00101     TRACE("(%p)->(ref before = %u)\n", This, refCount - 1);
00102 
00103     return refCount;
00104 }
00105 
00106 static ULONG WINAPI IAssemblyNameImpl_Release(IAssemblyName *iface)
00107 {
00108     IAssemblyNameImpl *This = impl_from_IAssemblyName(iface);
00109     ULONG refCount = InterlockedDecrement(&This->ref);
00110 
00111     TRACE("(%p)->(ref before = %u)\n", This, refCount + 1);
00112 
00113     if (!refCount)
00114     {
00115         HeapFree(GetProcessHeap(), 0, This->path);
00116         HeapFree(GetProcessHeap(), 0, This->displayname);
00117         HeapFree(GetProcessHeap(), 0, This->name);
00118         HeapFree(GetProcessHeap(), 0, This->culture);
00119         HeapFree(GetProcessHeap(), 0, This->procarch);
00120         HeapFree(GetProcessHeap(), 0, This);
00121     }
00122 
00123     return refCount;
00124 }
00125 
00126 static HRESULT WINAPI IAssemblyNameImpl_SetProperty(IAssemblyName *iface,
00127                                                     DWORD PropertyId,
00128                                                     LPVOID pvProperty,
00129                                                     DWORD cbProperty)
00130 {
00131     FIXME("(%p, %d, %p, %d) stub!\n", iface, PropertyId, pvProperty, cbProperty);
00132     return E_NOTIMPL;
00133 }
00134 
00135 static HRESULT WINAPI IAssemblyNameImpl_GetProperty(IAssemblyName *iface,
00136                                                     DWORD PropertyId,
00137                                                     LPVOID pvProperty,
00138                                                     LPDWORD pcbProperty)
00139 {
00140     IAssemblyNameImpl *name = impl_from_IAssemblyName(iface);
00141 
00142     TRACE("(%p, %d, %p, %p)\n", iface, PropertyId, pvProperty, pcbProperty);
00143 
00144     *((LPWSTR)pvProperty) = '\0';
00145 
00146     switch (PropertyId)
00147     {
00148         case ASM_NAME_NULL_PUBLIC_KEY:
00149         case ASM_NAME_NULL_PUBLIC_KEY_TOKEN:
00150             if (name->haspubkey)
00151                 return S_OK;
00152             return S_FALSE;
00153 
00154         case ASM_NAME_NULL_CUSTOM:
00155             return S_OK;
00156 
00157         case ASM_NAME_NAME:
00158             *pcbProperty = 0;
00159             if (name->name)
00160             {
00161                 lstrcpyW(pvProperty, name->name);
00162                 *pcbProperty = (lstrlenW(name->name) + 1) * 2;
00163             }
00164             break;
00165 
00166         case ASM_NAME_MAJOR_VERSION:
00167             *pcbProperty = 0;
00168             *((WORD *)pvProperty) = name->version[0];
00169             if (name->versize >= 1)
00170                 *pcbProperty = sizeof(WORD);
00171             break;
00172 
00173         case ASM_NAME_MINOR_VERSION:
00174             *pcbProperty = 0;
00175             *((WORD *)pvProperty) = name->version[1];
00176             if (name->versize >= 2)
00177                 *pcbProperty = sizeof(WORD);
00178             break;
00179 
00180         case ASM_NAME_BUILD_NUMBER:
00181             *pcbProperty = 0;
00182             *((WORD *)pvProperty) = name->version[2];
00183             if (name->versize >= 3)
00184                 *pcbProperty = sizeof(WORD);
00185             break;
00186 
00187         case ASM_NAME_REVISION_NUMBER:
00188             *pcbProperty = 0;
00189             *((WORD *)pvProperty) = name->version[3];
00190             if (name->versize >= 4)
00191                 *pcbProperty = sizeof(WORD);
00192             break;
00193 
00194         case ASM_NAME_CULTURE:
00195             *pcbProperty = 0;
00196             if (name->culture)
00197             {
00198                 lstrcpyW(pvProperty, name->culture);
00199                 *pcbProperty = (lstrlenW(name->culture) + 1) * 2;
00200             }
00201             break;
00202 
00203         case ASM_NAME_PUBLIC_KEY_TOKEN:
00204             *pcbProperty = 0;
00205             if (name->haspubkey)
00206             {
00207                 memcpy(pvProperty, name->pubkey, sizeof(DWORD) * 2);
00208                 *pcbProperty = sizeof(DWORD) * 2;
00209             }
00210             break;
00211 
00212         default:
00213             *pcbProperty = 0;
00214             break;
00215     }
00216 
00217     return S_OK;
00218 }
00219 
00220 static HRESULT WINAPI IAssemblyNameImpl_Finalize(IAssemblyName *iface)
00221 {
00222     FIXME("(%p) stub!\n", iface);
00223     return E_NOTIMPL;
00224 }
00225 
00226 static HRESULT WINAPI IAssemblyNameImpl_GetDisplayName(IAssemblyName *iface,
00227                                                        LPOLESTR szDisplayName,
00228                                                        LPDWORD pccDisplayName,
00229                                                        DWORD dwDisplayFlags)
00230 {
00231     IAssemblyNameImpl *name = impl_from_IAssemblyName(iface);
00232     WCHAR verstr[30];
00233     DWORD size;
00234     LPWSTR cultureval = 0;
00235 
00236     static const WCHAR equals[] = {'=',0};
00237 
00238     TRACE("(%p, %p, %p, %d)\n", iface, szDisplayName,
00239           pccDisplayName, dwDisplayFlags);
00240 
00241     if (dwDisplayFlags == 0)
00242     {
00243         if (!name->displayname || !*name->displayname)
00244             return FUSION_E_INVALID_NAME;
00245 
00246         size = min(*pccDisplayName, lstrlenW(name->displayname) + 1);
00247 
00248         lstrcpynW(szDisplayName, name->displayname, size);
00249         *pccDisplayName = size;
00250 
00251         return S_OK;
00252     }
00253 
00254     if (!name->name || !*name->name)
00255         return FUSION_E_INVALID_NAME;
00256 
00257     /* Verify buffer size is sufficient */
00258     size = lstrlenW(name->name) + 1;
00259 
00260     if ((dwDisplayFlags & ASM_DISPLAYF_VERSION) && (name->versize > 0))
00261     {
00262         static const WCHAR spec[] = {'%','d',0};
00263         static const WCHAR period[] = {'.',0};
00264         int i;
00265 
00266         wsprintfW(verstr, spec, name->version[0]);
00267 
00268         for (i = 1; i < name->versize; i++)
00269         {
00270             WCHAR value[6];
00271             wsprintfW(value, spec, name->version[i]);
00272 
00273             lstrcatW(verstr, period);
00274             lstrcatW(verstr, value);
00275         }
00276 
00277         size += lstrlenW(separator) + lstrlenW(version) + lstrlenW(equals) + lstrlenW(verstr);
00278     }
00279 
00280     if ((dwDisplayFlags & ASM_DISPLAYF_CULTURE) && (name->culture))
00281     {
00282         static const WCHAR neutral[] = {'n','e','u','t','r','a','l', 0};
00283 
00284         cultureval = (lstrlenW(name->culture) == 2) ? name->culture : (LPWSTR) neutral;
00285         size += lstrlenW(separator) + lstrlenW(culture) + lstrlenW(equals) + lstrlenW(cultureval);
00286     }
00287 
00288     if ((dwDisplayFlags & ASM_DISPLAYF_PUBLIC_KEY_TOKEN) && (name->haspubkey))
00289         size += lstrlenW(separator) + lstrlenW(pubkey) + lstrlenW(equals) + CHARS_PER_PUBKEY;
00290 
00291     if ((dwDisplayFlags & ASM_DISPLAYF_PROCESSORARCHITECTURE) && (name->procarch))
00292         size += lstrlenW(separator) + lstrlenW(procarch) + lstrlenW(equals) + lstrlenW(name->procarch);
00293 
00294     if (size > *pccDisplayName)
00295         return S_FALSE;
00296 
00297     /* Construct the string */
00298     lstrcpyW(szDisplayName, name->name);
00299 
00300     if ((dwDisplayFlags & ASM_DISPLAYF_VERSION) && (name->versize > 0))
00301     {
00302         lstrcatW(szDisplayName, separator);
00303 
00304         lstrcatW(szDisplayName, version);
00305         lstrcatW(szDisplayName, equals);
00306         lstrcatW(szDisplayName, verstr);
00307     }
00308 
00309     if ((dwDisplayFlags & ASM_DISPLAYF_CULTURE) && (name->culture))
00310     {
00311         lstrcatW(szDisplayName, separator);
00312 
00313         lstrcatW(szDisplayName, culture);
00314         lstrcatW(szDisplayName, equals);
00315         lstrcatW(szDisplayName, cultureval);
00316     }
00317 
00318     if ((dwDisplayFlags & ASM_DISPLAYF_PUBLIC_KEY_TOKEN) && (name->haspubkey))
00319     {
00320         WCHAR pkt[CHARS_PER_PUBKEY + 1];
00321         static const WCHAR spec[] = {'%','0','x','%','0','x','%','0','x',
00322             '%','0','x','%','0','x','%','0','x','%','0','x','%','0','x',0};
00323 
00324         lstrcatW(szDisplayName, separator);
00325 
00326         lstrcatW(szDisplayName, pubkey);
00327         lstrcatW(szDisplayName, equals);
00328 
00329         wsprintfW(pkt, spec, name->pubkey[0], name->pubkey[1], name->pubkey[2],
00330             name->pubkey[3], name->pubkey[4], name->pubkey[5], name->pubkey[6],
00331             name->pubkey[7]);
00332 
00333         lstrcatW(szDisplayName, pkt);
00334     }
00335 
00336     if ((dwDisplayFlags & ASM_DISPLAYF_PROCESSORARCHITECTURE) && (name->procarch))
00337     {
00338         lstrcatW(szDisplayName, separator);
00339 
00340         lstrcatW(szDisplayName, procarch);
00341         lstrcatW(szDisplayName, equals);
00342         lstrcatW(szDisplayName, name->procarch);
00343     }
00344 
00345     *pccDisplayName = size;
00346     return S_OK;
00347 }
00348 
00349 static HRESULT WINAPI IAssemblyNameImpl_Reserved(IAssemblyName *iface,
00350                                                  REFIID refIID,
00351                                                  IUnknown *pUnkReserved1,
00352                                                  IUnknown *pUnkReserved2,
00353                                                  LPCOLESTR szReserved,
00354                                                  LONGLONG llReserved,
00355                                                  LPVOID pvReserved,
00356                                                  DWORD cbReserved,
00357                                                  LPVOID *ppReserved)
00358 {
00359     TRACE("(%p, %s, %p, %p, %s, %x%08x, %p, %d, %p)\n", iface,
00360           debugstr_guid(refIID), pUnkReserved1, pUnkReserved2,
00361           debugstr_w(szReserved), (DWORD)(llReserved >> 32), (DWORD)llReserved,
00362           pvReserved, cbReserved, ppReserved);
00363 
00364     return E_NOTIMPL;
00365 }
00366 
00367 static HRESULT WINAPI IAssemblyNameImpl_GetName(IAssemblyName *iface,
00368                                                 LPDWORD lpcwBuffer,
00369                                                 WCHAR *pwzName)
00370 {
00371     IAssemblyNameImpl *name = impl_from_IAssemblyName(iface);
00372 
00373     TRACE("(%p, %p, %p)\n", iface, lpcwBuffer, pwzName);
00374 
00375     if (!name->name)
00376     {
00377         *pwzName = '\0';
00378         *lpcwBuffer = 0;
00379         return S_OK;
00380     }
00381 
00382     lstrcpyW(pwzName, name->name);
00383     *lpcwBuffer = lstrlenW(pwzName) + 1;
00384 
00385     return S_OK;
00386 }
00387 
00388 static HRESULT WINAPI IAssemblyNameImpl_GetVersion(IAssemblyName *iface,
00389                                                    LPDWORD pdwVersionHi,
00390                                                    LPDWORD pdwVersionLow)
00391 {
00392     IAssemblyNameImpl *name = impl_from_IAssemblyName(iface);
00393 
00394     TRACE("(%p, %p, %p)\n", iface, pdwVersionHi, pdwVersionLow);
00395 
00396     *pdwVersionHi = 0;
00397     *pdwVersionLow = 0;
00398 
00399     if (name->versize != 4)
00400         return FUSION_E_INVALID_NAME;
00401 
00402     *pdwVersionHi = (name->version[0] << 16) + name->version[1];
00403     *pdwVersionLow = (name->version[2] << 16) + name->version[3];
00404 
00405     return S_OK;
00406 }
00407 
00408 static HRESULT WINAPI IAssemblyNameImpl_IsEqual(IAssemblyName *iface,
00409                                                 IAssemblyName *pName,
00410                                                 DWORD dwCmpFlags)
00411 {
00412     FIXME("(%p, %p, %d) stub!\n", iface, pName, dwCmpFlags);
00413     return E_NOTIMPL;
00414 }
00415 
00416 static HRESULT WINAPI IAssemblyNameImpl_Clone(IAssemblyName *iface,
00417                                               IAssemblyName **pName)
00418 {
00419     FIXME("(%p, %p) stub!\n", iface, pName);
00420     return E_NOTIMPL;
00421 }
00422 
00423 static const IAssemblyNameVtbl AssemblyNameVtbl = {
00424     IAssemblyNameImpl_QueryInterface,
00425     IAssemblyNameImpl_AddRef,
00426     IAssemblyNameImpl_Release,
00427     IAssemblyNameImpl_SetProperty,
00428     IAssemblyNameImpl_GetProperty,
00429     IAssemblyNameImpl_Finalize,
00430     IAssemblyNameImpl_GetDisplayName,
00431     IAssemblyNameImpl_Reserved,
00432     IAssemblyNameImpl_GetName,
00433     IAssemblyNameImpl_GetVersion,
00434     IAssemblyNameImpl_IsEqual,
00435     IAssemblyNameImpl_Clone
00436 };
00437 
00438 /* Internal methods */
00439 static inline IAssemblyNameImpl *unsafe_impl_from_IAssemblyName(IAssemblyName *iface)
00440 {
00441     assert(iface->lpVtbl == &AssemblyNameVtbl);
00442 
00443     return impl_from_IAssemblyName(iface);
00444 }
00445 
00446 HRESULT IAssemblyName_SetPath(IAssemblyName *iface, LPCWSTR path)
00447 {
00448     IAssemblyNameImpl *name = unsafe_impl_from_IAssemblyName(iface);
00449 
00450     name->path = strdupW(path);
00451     if (!name->path)
00452         return E_OUTOFMEMORY;
00453 
00454     return S_OK;
00455 }
00456 
00457 HRESULT IAssemblyName_GetPath(IAssemblyName *iface, LPWSTR buf, ULONG *len)
00458 {
00459     ULONG buffer_size = *len;
00460     IAssemblyNameImpl *name = unsafe_impl_from_IAssemblyName(iface);
00461 
00462     if (!name->path)
00463         return S_OK;
00464 
00465     if (!buf)
00466         buffer_size = 0;
00467 
00468     *len = lstrlenW(name->path) + 1;
00469 
00470     if (*len <= buffer_size)
00471         lstrcpyW(buf, name->path);
00472     else
00473         return HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER);
00474 
00475     return S_OK;
00476 }
00477 
00478 static HRESULT parse_version(IAssemblyNameImpl *name, LPWSTR version)
00479 {
00480     LPWSTR beg, end;
00481     int i;
00482 
00483     for (i = 0, beg = version; i < 4; i++)
00484     {
00485         if (!*beg)
00486             return S_OK;
00487 
00488         end = strchrW(beg, '.');
00489 
00490         if (end) *end = '\0';
00491         name->version[i] = atolW(beg);
00492         name->versize++;
00493 
00494         if (!end && i < 3)
00495             return S_OK;
00496 
00497         beg = end + 1;
00498     }
00499 
00500     return S_OK;
00501 }
00502 
00503 static HRESULT parse_culture(IAssemblyNameImpl *name, LPCWSTR culture)
00504 {
00505     static const WCHAR empty[] = {0};
00506 
00507     if (lstrlenW(culture) == 2)
00508         name->culture = strdupW(culture);
00509     else
00510         name->culture = strdupW(empty);
00511 
00512     return S_OK;
00513 }
00514 
00515 static BOOL is_hex(WCHAR c)
00516 {
00517     return ((c >= 'a' && c <= 'f') ||
00518             (c >= 'A' && c <= 'F') ||
00519             (c >= '0' && c <= '9'));
00520 }
00521 
00522 static BYTE hextobyte(WCHAR c)
00523 {
00524     if(c >= '0' && c <= '9')
00525         return c - '0';
00526     if(c >= 'A' && c <= 'F')
00527         return c - 'A' + 10;
00528     if(c >= 'a' && c <= 'f')
00529         return c - 'a' + 10;
00530     return 0;
00531 }
00532 
00533 static HRESULT parse_pubkey(IAssemblyNameImpl *name, LPCWSTR pubkey)
00534 {
00535     int i;
00536     BYTE val;
00537 
00538     if (lstrlenW(pubkey) < CHARS_PER_PUBKEY)
00539         return FUSION_E_INVALID_NAME;
00540 
00541     for (i = 0; i < CHARS_PER_PUBKEY; i++)
00542         if (!is_hex(pubkey[i]))
00543             return FUSION_E_INVALID_NAME;
00544 
00545     name->haspubkey = TRUE;
00546 
00547     for (i = 0; i < CHARS_PER_PUBKEY; i += 2)
00548     {
00549         val = (hextobyte(pubkey[i]) << 4) + hextobyte(pubkey[i + 1]);
00550         name->pubkey[i / 2] = val;
00551     }
00552 
00553     return S_OK;
00554 }
00555 
00556 static HRESULT parse_display_name(IAssemblyNameImpl *name, LPCWSTR szAssemblyName)
00557 {
00558     LPWSTR str, save;
00559     LPWSTR ptr, ptr2;
00560     HRESULT hr = S_OK;
00561     BOOL done = FALSE;
00562 
00563     if (!szAssemblyName)
00564         return S_OK;
00565 
00566     name->displayname = strdupW(szAssemblyName);
00567     if (!name->displayname)
00568         return E_OUTOFMEMORY;
00569 
00570     str = strdupW(szAssemblyName);
00571     save = str;
00572     if (!str)
00573     {
00574         hr = E_OUTOFMEMORY;
00575         goto done;
00576     }
00577 
00578     ptr = strchrW(str, ',');
00579     if (ptr) *ptr = '\0';
00580 
00581     /* no ',' but ' ' only */
00582     if( !ptr && strchrW(str, ' ') )
00583     {
00584         hr = FUSION_E_INVALID_NAME;
00585         goto done;
00586     }
00587 
00588     name->name = strdupW(str);
00589     if (!name->name)
00590     {
00591         hr = E_OUTOFMEMORY;
00592         goto done;
00593     }
00594 
00595     if (!ptr)
00596         goto done;
00597 
00598     str = ptr + 2;
00599     while (!done)
00600     {
00601         ptr = strchrW(str, '=');
00602         if (!ptr)
00603         {
00604             hr = FUSION_E_INVALID_NAME;
00605             goto done;
00606         }
00607 
00608         *(ptr++) = '\0';
00609         if (!*ptr)
00610         {
00611             hr = FUSION_E_INVALID_NAME;
00612             goto done;
00613         }
00614 
00615         if (!(ptr2 = strstrW(ptr, separator)))
00616         {
00617             if (!(ptr2 = strchrW(ptr, '\0')))
00618             {
00619                 hr = FUSION_E_INVALID_NAME;
00620                 goto done;
00621             }
00622 
00623             done = TRUE;
00624         }
00625 
00626         *ptr2 = '\0';
00627 
00628         while (*str == ' ') str++;
00629 
00630         if (!lstrcmpW(str, version))
00631             hr = parse_version(name, ptr);
00632         else if (!lstrcmpW(str, culture))
00633             hr = parse_culture(name, ptr);
00634         else if (!lstrcmpW(str, pubkey))
00635             hr = parse_pubkey(name, ptr);
00636         else if (!lstrcmpW(str, procarch))
00637         {
00638             name->procarch = strdupW(ptr);
00639             if (!name->procarch)
00640                 hr = E_OUTOFMEMORY;
00641         }
00642 
00643         if (FAILED(hr))
00644             goto done;
00645 
00646         str = ptr2 + 1;
00647     }
00648 
00649 done:
00650     HeapFree(GetProcessHeap(), 0, save);
00651     if (FAILED(hr))
00652     {
00653         HeapFree(GetProcessHeap(), 0, name->displayname);
00654         HeapFree(GetProcessHeap(), 0, name->name);
00655     }
00656     return hr;
00657 }
00658 
00659 /******************************************************************
00660  *  CreateAssemblyNameObject   (FUSION.@)
00661  */
00662 HRESULT WINAPI CreateAssemblyNameObject(LPASSEMBLYNAME *ppAssemblyNameObj,
00663                                         LPCWSTR szAssemblyName, DWORD dwFlags,
00664                                         LPVOID pvReserved)
00665 {
00666     IAssemblyNameImpl *name;
00667     HRESULT hr;
00668 
00669     TRACE("(%p, %s, %08x, %p)\n", ppAssemblyNameObj,
00670           debugstr_w(szAssemblyName), dwFlags, pvReserved);
00671 
00672     if (!ppAssemblyNameObj)
00673         return E_INVALIDARG;
00674 
00675     if ((dwFlags & CANOF_PARSE_DISPLAY_NAME) &&
00676         (!szAssemblyName || !*szAssemblyName))
00677         return E_INVALIDARG;
00678 
00679     name = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IAssemblyNameImpl));
00680     if (!name)
00681         return E_OUTOFMEMORY;
00682 
00683     name->IAssemblyName_iface.lpVtbl = &AssemblyNameVtbl;
00684     name->ref = 1;
00685 
00686     hr = parse_display_name(name, szAssemblyName);
00687     if (FAILED(hr))
00688     {
00689         HeapFree(GetProcessHeap(), 0, name);
00690         return hr;
00691     }
00692 
00693     *ppAssemblyNameObj = &name->IAssemblyName_iface;
00694 
00695     return S_OK;
00696 }

Generated on Sun May 27 2012 04:23:33 for ReactOS by doxygen 1.7.6.1

ReactOS is a registered trademark or a trademark of ReactOS Foundation in the United States and other countries.