BOOL path_find_symbol_file(const struct process* pcs, PCSTR full_path, const GUID* guid, DWORD dw1, DWORD dw2, PSTR buffer, BOOL* is_unmatched) { struct module_find mf; WCHAR full_pathW[MAX_PATH]; WCHAR tmp[MAX_PATH]; WCHAR* ptr; const WCHAR* filename; WCHAR* searchPath = pcs->search_path; TRACE("(pcs = %p, full_path = %s, guid = %s, dw1 = 0x%08x, dw2 = 0x%08x, buffer = %p)\n", pcs, debugstr_a(full_path), debugstr_guid(guid), dw1, dw2, buffer); mf.guid = guid; mf.dw1 = dw1; mf.dw2 = dw2; mf.matched = 0; MultiByteToWideChar(CP_ACP, 0, full_path, -1, full_pathW, MAX_PATH); filename = file_nameW(full_pathW); mf.kind = module_get_type_by_name(filename); *is_unmatched = FALSE; /* first check full path to file */ if (module_find_cb(full_pathW, &mf)) { WideCharToMultiByte(CP_ACP, 0, full_pathW, -1, buffer, MAX_PATH, NULL, NULL); return TRUE; } while (searchPath) { ptr = strchrW(searchPath, ';'); if (ptr) { memcpy(tmp, searchPath, (ptr - searchPath) * sizeof(WCHAR)); tmp[ptr - searchPath] = '\0'; searchPath = ptr + 1; } else { strcpyW(tmp, searchPath); searchPath = NULL; } if (do_searchW(filename, tmp, FALSE, module_find_cb, &mf)) { /* return first fully matched file */ WideCharToMultiByte(CP_ACP, 0, tmp, -1, buffer, MAX_PATH, NULL, NULL); return TRUE; } } /* if no fully matching file is found, return the best matching file if any */ if ((dbghelp_options & SYMOPT_LOAD_ANYTHING) && mf.matched) { WideCharToMultiByte(CP_ACP, 0, mf.filename, -1, buffer, MAX_PATH, NULL, NULL); *is_unmatched = TRUE; return TRUE; } return FALSE; }
/*********************************************************************** * WININET_GetSetPassword */ static BOOL WININET_GetSetPassword( HWND hdlg, LPCWSTR szServer, LPCWSTR szRealm, BOOL bSet ) { WCHAR szResource[0x80], szUserPass[0x40]; LPWSTR p; HWND hUserItem, hPassItem; DWORD r, dwMagic = 19; UINT r_len, u_len; WORD sz; static const WCHAR szColon[] = { ':',0 }; static const WCHAR szbs[] = { '/', 0 }; hUserItem = GetDlgItem( hdlg, IDC_USERNAME ); hPassItem = GetDlgItem( hdlg, IDC_PASSWORD ); /* now try fetch the username and password */ lstrcpyW( szResource, szServer); lstrcatW( szResource, szbs); lstrcatW( szResource, szRealm); /* * WNetCachePassword is only concerned with the length * of the data stored (which we tell it) and it does * not use strlen() internally so we can add WCHAR data * instead of ASCII data and get it back the same way. */ if( bSet ) { szUserPass[0] = 0; GetWindowTextW( hUserItem, szUserPass, (sizeof szUserPass-1)/sizeof(WCHAR) ); lstrcatW(szUserPass, szColon); u_len = strlenW( szUserPass ); GetWindowTextW( hPassItem, szUserPass+u_len, (sizeof szUserPass)/sizeof(WCHAR)-u_len ); r_len = (strlenW( szResource ) + 1)*sizeof(WCHAR); u_len = (strlenW( szUserPass ) + 1)*sizeof(WCHAR); r = WNetCachePassword( (CHAR*)szResource, r_len, (CHAR*)szUserPass, u_len, dwMagic, 0 ); return ( r == WN_SUCCESS ); } sz = sizeof szUserPass; r_len = (strlenW( szResource ) + 1)*sizeof(WCHAR); r = WNetGetCachedPassword( (CHAR*)szResource, r_len, (CHAR*)szUserPass, &sz, dwMagic ); if( r != WN_SUCCESS ) return FALSE; p = strchrW( szUserPass, ':' ); if( p ) { *p = 0; SetWindowTextW( hUserItem, szUserPass ); SetWindowTextW( hPassItem, p+1 ); } return TRUE; }
/* find a character from a set in reverse without the string having to be null-terminated */ static inline WCHAR *memrpbrkW(const WCHAR *ptr, size_t n, const WCHAR *accept) { const WCHAR *end, *ret = NULL; for (end = ptr + n; ptr < end; ptr++) if (strchrW(accept, *ptr)) ret = ptr; return (WCHAR *)ret; }
static HRESULT HttpProtocol_start_downloading(Protocol *prot) { HttpProtocol *This = impl_from_Protocol(prot); LPWSTR content_type, content_length, ranges; DWORD len = sizeof(DWORD); DWORD status_code; BOOL res; HRESULT hres; static const WCHAR wszDefaultContentType[] = {'t','e','x','t','/','h','t','m','l',0}; if(!This->http_negotiate) { WARN("Expected IHttpNegotiate pointer to be non-NULL\n"); return S_OK; } res = HttpQueryInfoW(This->base.request, HTTP_QUERY_STATUS_CODE | HTTP_QUERY_FLAG_NUMBER, &status_code, &len, NULL); if(res) { LPWSTR response_headers = query_http_info(This, HTTP_QUERY_RAW_HEADERS_CRLF); if(response_headers) { hres = IHttpNegotiate_OnResponse(This->http_negotiate, status_code, response_headers, NULL, NULL); heap_free(response_headers); if (hres != S_OK) { WARN("IHttpNegotiate_OnResponse failed: %08x\n", hres); return S_OK; } } }else { WARN("HttpQueryInfo failed: %d\n", GetLastError()); } ranges = query_http_info(This, HTTP_QUERY_ACCEPT_RANGES); if(ranges) { IInternetProtocolSink_ReportProgress(This->base.protocol_sink, BINDSTATUS_ACCEPTRANGES, NULL); heap_free(ranges); } content_type = query_http_info(This, HTTP_QUERY_CONTENT_TYPE); if(content_type) { /* remove the charset, if present */ LPWSTR p = strchrW(content_type, ';'); if (p) *p = '\0'; IInternetProtocolSink_ReportProgress(This->base.protocol_sink, (This->base.bindf & BINDF_FROMURLMON) ? BINDSTATUS_MIMETYPEAVAILABLE : BINDSTATUS_RAWMIMETYPE, content_type); heap_free(content_type); }else { WARN("HttpQueryInfo failed: %d\n", GetLastError()); IInternetProtocolSink_ReportProgress(This->base.protocol_sink, (This->base.bindf & BINDF_FROMURLMON) ? BINDSTATUS_MIMETYPEAVAILABLE : BINDSTATUS_RAWMIMETYPE, wszDefaultContentType); } content_length = query_http_info(This, HTTP_QUERY_CONTENT_LENGTH); if(content_length) { This->base.content_length = atoiW(content_length); heap_free(content_length); } return S_OK; }
static HRESULT HttpProtocol_start_downloading(Protocol *prot) { HttpProtocol *This = impl_from_Protocol(prot); LPWSTR content_type, content_length, ranges; DWORD len = sizeof(DWORD); DWORD status_code; BOOL res; HRESULT hres; static const WCHAR wszDefaultContentType[] = {'t','e','x','t','/','h','t','m','l',0}; if(!This->http_negotiate) { WARN("Expected IHttpNegotiate pointer to be non-NULL\n"); return S_OK; } res = HttpQueryInfoW(This->base.request, HTTP_QUERY_STATUS_CODE | HTTP_QUERY_FLAG_NUMBER, &status_code, &len, NULL); if(res) { WCHAR *response_headers; if((This->base.bind_info.dwOptions & BINDINFO_OPTIONS_DISABLEAUTOREDIRECTS) && is_redirect_response(status_code)) { WCHAR *location; TRACE("Got redirect with disabled auto redirects\n"); location = query_http_info(This, HTTP_QUERY_LOCATION); This->base.flags |= FLAG_RESULT_REPORTED | FLAG_LAST_DATA_REPORTED; IInternetProtocolSink_ReportResult(This->base.protocol_sink, INET_E_REDIRECT_FAILED, 0, location); heap_free(location); return INET_E_REDIRECT_FAILED; } response_headers = query_http_info(This, HTTP_QUERY_RAW_HEADERS_CRLF); if(response_headers) { hres = IHttpNegotiate_OnResponse(This->http_negotiate, status_code, response_headers, NULL, NULL); heap_free(response_headers); if (hres != S_OK) { WARN("IHttpNegotiate_OnResponse failed: %08x\n", hres); return S_OK; } } }else { WARN("HttpQueryInfo failed: %d\n", GetLastError()); } ranges = query_http_info(This, HTTP_QUERY_ACCEPT_RANGES); if(ranges) { IInternetProtocolSink_ReportProgress(This->base.protocol_sink, BINDSTATUS_ACCEPTRANGES, NULL); heap_free(ranges); } content_type = query_http_info(This, HTTP_QUERY_CONTENT_TYPE); if(content_type) { /* remove the charset, if present */ LPWSTR p = strchrW(content_type, ';'); if (p) *p = '\0'; IInternetProtocolSink_ReportProgress(This->base.protocol_sink, (This->base.bindf & BINDF_FROMURLMON) ? BINDSTATUS_MIMETYPEAVAILABLE : BINDSTATUS_RAWMIMETYPE, content_type); heap_free(content_type); }else { WARN("HttpQueryInfo failed: %d\n", GetLastError()); IInternetProtocolSink_ReportProgress(This->base.protocol_sink, (This->base.bindf & BINDF_FROMURLMON) ? BINDSTATUS_MIMETYPEAVAILABLE : BINDSTATUS_RAWMIMETYPE, wszDefaultContentType); } content_length = query_http_info(This, HTTP_QUERY_CONTENT_LENGTH); if(content_length) { This->base.content_length = atoiW(content_length); heap_free(content_length); } return S_OK; }
BOOL validate_service_name(LPCWSTR name) { return (name && name[0] && !strchrW(name, '/') && !strchrW(name, '\\')); }
/* Fills in sig with the values from the Signature table, where name is the * signature to find. Upon return, sig->File will be NULL if the record is not * found, and not NULL if it is found. * Warning: clears all fields in sig! * Returns ERROR_SUCCESS upon success (where not finding the record counts as * success), something else on error. */ static UINT get_signature( MSIPACKAGE *package, MSISIGNATURE *sig, const WCHAR *name ) { static const WCHAR query[] = { 's','e','l','e','c','t',' ','*',' ', 'f','r','o','m',' ', 'S','i','g','n','a','t','u','r','e',' ', 'w','h','e','r','e',' ','S','i','g','n','a','t','u','r','e',' ','=',' ', '\'','%','s','\'',0}; LPWSTR minVersion, maxVersion, p; MSIRECORD *row; DWORD time; TRACE("package %p, sig %p\n", package, sig); memset(sig, 0, sizeof(*sig)); sig->Name = name; row = MSI_QueryGetRecord( package->db, query, name ); if (!row) { TRACE("failed to query signature for %s\n", debugstr_w(name)); return ERROR_SUCCESS; } /* get properties */ sig->File = msi_dup_record_field(row,2); if ((p = strchrW(sig->File, '|'))) { p++; memmove(sig->File, p, (strlenW(p) + 1) * sizeof(WCHAR)); } minVersion = msi_dup_record_field(row,3); if (minVersion) { msi_parse_version_string( minVersion, &sig->MinVersionMS, &sig->MinVersionLS ); msi_free( minVersion ); } maxVersion = msi_dup_record_field(row,4); if (maxVersion) { msi_parse_version_string( maxVersion, &sig->MaxVersionMS, &sig->MaxVersionLS ); msi_free( maxVersion ); } sig->MinSize = MSI_RecordGetInteger(row,5); if (sig->MinSize == MSI_NULL_INTEGER) sig->MinSize = 0; sig->MaxSize = MSI_RecordGetInteger(row,6); if (sig->MaxSize == MSI_NULL_INTEGER) sig->MaxSize = 0; sig->Languages = msi_dup_record_field(row,9); time = MSI_RecordGetInteger(row,7); if (time != MSI_NULL_INTEGER) DosDateTimeToFileTime(HIWORD(time), LOWORD(time), &sig->MinTime); time = MSI_RecordGetInteger(row,8); if (time != MSI_NULL_INTEGER) DosDateTimeToFileTime(HIWORD(time), LOWORD(time), &sig->MaxTime); TRACE("Found file name %s for Signature_ %s;\n", debugstr_w(sig->File), debugstr_w(name)); TRACE("MinVersion is %d.%d.%d.%d\n", HIWORD(sig->MinVersionMS), LOWORD(sig->MinVersionMS), HIWORD(sig->MinVersionLS), LOWORD(sig->MinVersionLS)); TRACE("MaxVersion is %d.%d.%d.%d\n", HIWORD(sig->MaxVersionMS), LOWORD(sig->MaxVersionMS), HIWORD(sig->MaxVersionLS), LOWORD(sig->MaxVersionLS)); TRACE("MinSize is %d, MaxSize is %d;\n", sig->MinSize, sig->MaxSize); TRACE("Languages is %s\n", debugstr_w(sig->Languages)); msiobj_release( &row->hdr ); return ERROR_SUCCESS; }
static int reg_add(WCHAR *key_name, WCHAR *value_name, BOOL value_empty, WCHAR *type, WCHAR separator, WCHAR *data, BOOL force) { LPWSTR p; HKEY root,subkey; if (!sane_path(key_name)) return 1; p = strchrW(key_name,'\\'); if (!p) { output_message(STRING_INVALID_KEY); return 1; } p++; root = path_get_rootkey(key_name); if (!root) { output_message(STRING_INVALID_KEY); return 1; } if (value_name && value_empty) { output_message(STRING_INVALID_CMDLINE); return 1; } if(RegCreateKeyW(root,p,&subkey)!=ERROR_SUCCESS) { output_message(STRING_INVALID_KEY); return 1; } if (value_name || data) { DWORD reg_type; DWORD reg_count = 0; BYTE* reg_data = NULL; if (!force) { if (RegQueryValueExW(subkey, value_name, NULL, NULL, NULL, NULL) == ERROR_SUCCESS) { if (!ask_confirm(STRING_OVERWRITE_VALUE, value_name)) { RegCloseKey(subkey); output_message(STRING_CANCELLED); return 0; } } } reg_type = wchar_get_type(type); if (reg_type == ~0u) { RegCloseKey(subkey); output_message(STRING_UNSUPPORTED_TYPE, type); return 1; } if (reg_type == REG_DWORD && !data) { RegCloseKey(subkey); output_message(STRING_INVALID_CMDLINE); return 1; } if (data && !(reg_data = get_regdata(data, reg_type, separator, ®_count))) { RegCloseKey(subkey); return 1; } RegSetValueExW(subkey,value_name,0,reg_type,reg_data,reg_count); HeapFree(GetProcessHeap(),0,reg_data); } RegCloseKey(subkey); output_message(STRING_SUCCESS); return 0; }
static int reg_delete(WCHAR *key_name, WCHAR *value_name, BOOL value_empty, BOOL value_all, BOOL force) { LPWSTR p; HKEY root,subkey; if (!sane_path(key_name)) return 1; p = strchrW(key_name,'\\'); if (!p) { output_message(STRING_INVALID_KEY); return 1; } p++; root = path_get_rootkey(key_name); if (!root) { output_message(STRING_INVALID_KEY); return 1; } if ((value_name && value_empty) || (value_name && value_all) || (value_empty && value_all)) { output_message(STRING_INVALID_CMDLINE); return 1; } if (!force) { BOOL ret; if (value_name || value_empty) ret = ask_confirm(STRING_DELETE_VALUE, value_name); else if (value_all) ret = ask_confirm(STRING_DELETE_VALUEALL, key_name); else ret = ask_confirm(STRING_DELETE_SUBKEY, key_name); if (!ret) { output_message(STRING_CANCELLED); return 0; } } /* Delete subtree only if no /v* option is given */ if (!value_name && !value_empty && !value_all) { if (RegDeleteTreeW(root,p)!=ERROR_SUCCESS) { output_message(STRING_CANNOT_FIND); return 1; } output_message(STRING_SUCCESS); return 0; } if(RegOpenKeyW(root,p,&subkey)!=ERROR_SUCCESS) { output_message(STRING_CANNOT_FIND); return 1; } if (value_all) { LPWSTR szValue; DWORD maxValue; DWORD count; LONG rc; rc = RegQueryInfoKeyW(subkey, NULL, NULL, NULL, NULL, NULL, NULL, NULL, &maxValue, NULL, NULL, NULL); if (rc != ERROR_SUCCESS) { /* FIXME: failure */ RegCloseKey(subkey); return 1; } maxValue++; szValue = HeapAlloc(GetProcessHeap(),0,maxValue*sizeof(WCHAR)); while (1) { count = maxValue; rc = RegEnumValueW(subkey, 0, szValue, &count, NULL, NULL, NULL, NULL); if (rc == ERROR_SUCCESS) { rc = RegDeleteValueW(subkey, szValue); if (rc != ERROR_SUCCESS) break; } else break; } if (rc != ERROR_SUCCESS) { /* FIXME delete failed */ } } else if (value_name) { if (RegDeleteValueW(subkey,value_name) != ERROR_SUCCESS) { RegCloseKey(subkey); output_message(STRING_CANNOT_FIND); return 1; } } else if (value_empty) { RegSetValueExW(subkey,NULL,0,REG_SZ,NULL,0); } RegCloseKey(subkey); output_message(STRING_SUCCESS); return 0; }
static LONG RegpOpenOrCreateKey( IN HKEY hParentKey, IN PCWSTR KeyName, IN BOOL AllowCreation, OUT PHKEY Key) { PWSTR LocalKeyName; PWSTR End; UNICODE_STRING KeyString; NTSTATUS Status; MEMKEY ParentKey; MEMKEY CurrentKey; PLIST_ENTRY Ptr; PCM_KEY_NODE SubKeyCell; HCELL_INDEX BlockOffset; DPRINT("RegpCreateOpenKey('%S')\n", KeyName); if (*KeyName == L'\\') { KeyName++; ParentKey = RootKey; } else if (hParentKey == NULL) { ParentKey = RootKey; } else { ParentKey = HKEY_TO_MEMKEY(RootKey); } LocalKeyName = (PWSTR)KeyName; for (;;) { End = (PWSTR)strchrW(LocalKeyName, '\\'); if (End) { KeyString.Buffer = LocalKeyName; KeyString.Length = KeyString.MaximumLength = (USHORT)((ULONG_PTR)End - (ULONG_PTR)LocalKeyName); } else RtlInitUnicodeString(&KeyString, LocalKeyName); /* Redirect from 'CurrentControlSet' to 'ControlSet001' */ if (!strncmpW(LocalKeyName, L"CurrentControlSet", 17) && ParentKey->NameSize == 12 && !memcmp(ParentKey->Name, L"SYSTEM", 12)) RtlInitUnicodeString(&KeyString, L"ControlSet001"); /* Check subkey in memory structure */ Ptr = ParentKey->SubKeyList.Flink; while (Ptr != &ParentKey->SubKeyList) { CurrentKey = CONTAINING_RECORD(Ptr, KEY, KeyList); if (CurrentKey->NameSize == KeyString.Length && memcmp(CurrentKey->Name, KeyString.Buffer, KeyString.Length) == 0) { goto nextsubkey; } Ptr = Ptr->Flink; } Status = CmiScanForSubKey( ParentKey->RegistryHive, ParentKey->KeyCell, &KeyString, OBJ_CASE_INSENSITIVE, &SubKeyCell, &BlockOffset); if (AllowCreation && Status == STATUS_OBJECT_NAME_NOT_FOUND) { Status = CmiAddSubKey( ParentKey->RegistryHive, ParentKey->KeyCell, ParentKey->KeyCellOffset, &KeyString, 0, &SubKeyCell, &BlockOffset); } if (!NT_SUCCESS(Status)) return ERROR_UNSUCCESSFUL; /* Now, SubKeyCell/BlockOffset are valid */ CurrentKey = CreateInMemoryStructure( ParentKey->RegistryHive, BlockOffset, &KeyString); if (!CurrentKey) return ERROR_OUTOFMEMORY; /* Add CurrentKey in ParentKey */ InsertTailList(&ParentKey->SubKeyList, &CurrentKey->KeyList); ParentKey->SubKeyCount++; nextsubkey: ParentKey = CurrentKey; if (End) LocalKeyName = End + 1; else break; } *Key = MEMKEY_TO_HKEY(ParentKey); return ERROR_SUCCESS; }
BOOL GetAddress(LPCWSTR lpszServerName, INTERNET_PORT nServerPort, struct sockaddr *psa, socklen_t *sa_len) { WCHAR *found; char *name; int len, sz; #ifdef HAVE_GETADDRINFO struct addrinfo *res, hints; int ret; #else struct hostent *phe; struct sockaddr_in *sin = (struct sockaddr_in *)psa; #endif TRACE("%s\n", debugstr_w(lpszServerName)); /* Validate server name first * Check if there is sth. like * pinger.macromedia.com:80 * if yes, eliminate the :80.... */ found = strchrW(lpszServerName, ':'); if (found) len = found - lpszServerName; else len = strlenW(lpszServerName); sz = WideCharToMultiByte( CP_UNIXCP, 0, lpszServerName, len, NULL, 0, NULL, NULL ); if (!(name = HeapAlloc( GetProcessHeap(), 0, sz + 1 ))) return FALSE; WideCharToMultiByte( CP_UNIXCP, 0, lpszServerName, len, name, sz, NULL, NULL ); name[sz] = 0; #ifdef HAVE_GETADDRINFO memset( &hints, 0, sizeof(struct addrinfo) ); /* Prefer IPv4 to IPv6 addresses, since some servers do not listen on * their IPv6 addresses even though they have IPv6 addresses in the DNS. */ hints.ai_family = AF_INET; ret = getaddrinfo( name, NULL, &hints, &res ); HeapFree( GetProcessHeap(), 0, name ); if (ret != 0) { TRACE("failed to get IPv4 address of %s (%s), retrying with IPv6\n", debugstr_w(lpszServerName), gai_strerror(ret)); hints.ai_family = AF_INET6; ret = getaddrinfo( name, NULL, &hints, &res ); if (ret != 0) { TRACE("failed to get address of %s (%s)\n", debugstr_w(lpszServerName), gai_strerror(ret)); return FALSE; } } if (*sa_len < res->ai_addrlen) { WARN("address too small\n"); freeaddrinfo( res ); return FALSE; } *sa_len = res->ai_addrlen; memcpy( psa, res->ai_addr, res->ai_addrlen ); /* Copy port */ switch (res->ai_family) { case AF_INET: ((struct sockaddr_in *)psa)->sin_port = htons(nServerPort); break; case AF_INET6: ((struct sockaddr_in6 *)psa)->sin6_port = htons(nServerPort); break; } freeaddrinfo( res ); #else EnterCriticalSection( &cs_gethostbyname ); phe = gethostbyname(name); HeapFree( GetProcessHeap(), 0, name ); if (NULL == phe) { TRACE("failed to get address of %s (%d)\n", debugstr_w(lpszServerName), h_errno); LeaveCriticalSection( &cs_gethostbyname ); return FALSE; } if (*sa_len < sizeof(struct sockaddr_in)) { WARN("address too small\n"); LeaveCriticalSection( &cs_gethostbyname ); return FALSE; } *sa_len = sizeof(struct sockaddr_in); memset(sin,0,sizeof(struct sockaddr_in)); memcpy((char *)&sin->sin_addr, phe->h_addr, phe->h_length); sin->sin_family = phe->h_addrtype; sin->sin_port = htons(nServerPort); LeaveCriticalSection( &cs_gethostbyname ); #endif return TRUE; }
/*********************************************************************** * HlinkCreateFromString (HLINK.@) */ HRESULT WINAPI HlinkCreateFromString( LPCWSTR pwzTarget, LPCWSTR pwzLocation, LPCWSTR pwzFriendlyName, IHlinkSite* pihlsite, DWORD dwSiteData, IUnknown* piunkOuter, REFIID riid, void** ppvObj) { IHlink *hl = NULL; HRESULT r = S_OK; WCHAR *hash, *tgt; const WCHAR *loc; TRACE("%s %s %s %p %i %p %s %p\n", debugstr_w(pwzTarget), debugstr_w(pwzLocation), debugstr_w(pwzFriendlyName), pihlsite, dwSiteData, piunkOuter, debugstr_guid(riid), ppvObj); r = CoCreateInstance(&CLSID_StdHlink, piunkOuter, CLSCTX_INPROC_SERVER, riid, (LPVOID*)&hl); if (FAILED(r)) return r; if (pwzTarget) { hash = strchrW(pwzTarget, '#'); if (hash) { if (hash == pwzTarget) tgt = NULL; else { int tgt_len = hash - pwzTarget; tgt = heap_alloc((tgt_len + 1) * sizeof(WCHAR)); if (!tgt) return E_OUTOFMEMORY; memcpy(tgt, pwzTarget, tgt_len * sizeof(WCHAR)); tgt[tgt_len] = 0; } if (!pwzLocation) loc = hash + 1; else loc = pwzLocation; } else { tgt = hlink_strdupW(pwzTarget); if (!tgt) return E_OUTOFMEMORY; loc = pwzLocation; } } else { tgt = NULL; loc = pwzLocation; } IHlink_SetStringReference(hl, HLINKSETF_TARGET | HLINKSETF_LOCATION, tgt, loc); heap_free(tgt); if (pwzFriendlyName) IHlink_SetFriendlyName(hl, pwzFriendlyName); if (pihlsite) IHlink_SetHlinkSite(hl, pihlsite, dwSiteData); TRACE("Returning %i\n",r); *ppvObj = hl; return r; }
/* main desktop management function */ void manage_desktop( WCHAR *arg ) { static const WCHAR messageW[] = {'M','e','s','s','a','g','e',0}; HDESK desktop = 0; GUID guid; MSG msg; HWND hwnd, msg_hwnd; HMODULE graphics_driver; unsigned int width, height; WCHAR *cmdline = NULL, *driver = NULL; WCHAR *p = arg; const WCHAR *name = NULL; BOOL enable_shell = FALSE; /* get the rest of the command line (if any) */ while (*p && !isspace(*p)) p++; if (*p) { *p++ = 0; while (*p && isspace(*p)) p++; if (*p) cmdline = p; } /* parse the desktop option */ /* the option is of the form /desktop=name[,widthxheight[,driver]] */ if (*arg == '=' || *arg == ',') { arg++; name = arg; if ((p = strchrW( arg, ',' ))) { *p++ = 0; if ((driver = strchrW( p, ',' ))) *driver++ = 0; } if (!p || !parse_size( p, &width, &height )) get_default_desktop_size( name, &width, &height ); } else if ((name = get_default_desktop_name())) { if (!get_default_desktop_size( name, &width, &height )) width = height = 0; } if (name) enable_shell = get_default_enable_shell( name ); if (name && width && height) { if (!(desktop = CreateDesktopW( name, NULL, NULL, 0, DESKTOP_ALL_ACCESS, NULL ))) { WINE_ERR( "failed to create desktop %s error %d\n", wine_dbgstr_w(name), GetLastError() ); ExitProcess( 1 ); } SetThreadDesktop( desktop ); } UuidCreate( &guid ); TRACE( "display guid %s\n", debugstr_guid(&guid) ); graphics_driver = load_graphics_driver( driver, &guid ); /* create the desktop window */ hwnd = CreateWindowExW( 0, DESKTOP_CLASS_ATOM, NULL, WS_POPUP | WS_CLIPSIBLINGS | WS_CLIPCHILDREN, 0, 0, 0, 0, 0, 0, 0, &guid ); /* create the HWND_MESSAGE parent */ msg_hwnd = CreateWindowExW( 0, messageW, NULL, WS_POPUP | WS_CLIPSIBLINGS | WS_CLIPCHILDREN, 0, 0, 100, 100, 0, 0, 0, NULL ); if (hwnd == GetDesktopWindow()) { using_root = !desktop || !create_desktop( graphics_driver, name, width, height ); SetWindowLongPtrW( hwnd, GWLP_WNDPROC, (LONG_PTR)desktop_wnd_proc ); SendMessageW( hwnd, WM_SETICON, ICON_BIG, (LPARAM)LoadIconW( 0, MAKEINTRESOURCEW(OIC_WINLOGO))); if (name) set_desktop_window_title( hwnd, name ); SetWindowPos( hwnd, 0, GetSystemMetrics(SM_XVIRTUALSCREEN), GetSystemMetrics(SM_YVIRTUALSCREEN), GetSystemMetrics(SM_CXVIRTUALSCREEN), GetSystemMetrics(SM_CYVIRTUALSCREEN), SWP_SHOWWINDOW ); SystemParametersInfoW( SPI_SETDESKWALLPAPER, 0, NULL, FALSE ); ClipCursor( NULL ); initialize_display_settings(); initialize_appbar(); if (graphics_driver) { HMODULE shell32; void (WINAPI *pShellDDEInit)( BOOL ); if (using_root) enable_shell = FALSE; initialize_systray( graphics_driver, using_root, enable_shell ); if (!using_root) initialize_launchers( hwnd ); if ((shell32 = LoadLibraryA( "shell32.dll" )) && (pShellDDEInit = (void *)GetProcAddress( shell32, (LPCSTR)188))) { pShellDDEInit( TRUE ); } } } else { DestroyWindow( hwnd ); /* someone beat us to it */ hwnd = 0; } if (GetAncestor( msg_hwnd, GA_PARENT )) DestroyWindow( msg_hwnd ); /* someone beat us to it */ /* if we have a command line, execute it */ if (cmdline) { STARTUPINFOW si; PROCESS_INFORMATION pi; memset( &si, 0, sizeof(si) ); si.cb = sizeof(si); WINE_TRACE( "starting %s\n", wine_dbgstr_w(cmdline) ); if (CreateProcessW( NULL, cmdline, NULL, NULL, FALSE, 0, NULL, NULL, &si, &pi )) { CloseHandle( pi.hThread ); CloseHandle( pi.hProcess ); } } /* run the desktop message loop */ if (hwnd) { WINE_TRACE( "desktop message loop starting on hwnd %p\n", hwnd ); while (GetMessageW( &msg, 0, 0, 0 )) DispatchMessageW( &msg ); WINE_TRACE( "desktop message loop exiting for hwnd %p\n", hwnd ); } ExitProcess( 0 ); }
static HMODULE load_graphics_driver( const WCHAR *driver, const GUID *guid ) { static const WCHAR device_keyW[] = { 'S','y','s','t','e','m','\\', 'C','u','r','r','e','n','t','C','o','n','t','r','o','l','S','e','t','\\', 'C','o','n','t','r','o','l','\\', 'V','i','d','e','o','\\', '{','%','0','8','x','-','%','0','4','x','-','%','0','4','x','-', '%','0','2','x','%','0','2','x','-','%','0','2','x','%','0','2','x','%','0','2','x', '%','0','2','x','%','0','2','x','%','0','2','x','}','\\','0','0','0','0',0}; static const WCHAR graphics_driverW[] = {'G','r','a','p','h','i','c','s','D','r','i','v','e','r',0}; static const WCHAR driversW[] = {'S','o','f','t','w','a','r','e','\\', 'W','i','n','e','\\','D','r','i','v','e','r','s',0}; static const WCHAR graphicsW[] = {'G','r','a','p','h','i','c','s',0}; static const WCHAR drv_formatW[] = {'w','i','n','e','%','s','.','d','r','v',0}; WCHAR buffer[MAX_PATH], libname[32], *name, *next; WCHAR key[sizeof(device_keyW)/sizeof(WCHAR) + 39]; HMODULE module = 0; HKEY hkey; char error[80]; if (!driver) { strcpyW( buffer, default_driver ); /* @@ Wine registry key: HKCU\Software\Wine\Drivers */ if (!RegOpenKeyW( HKEY_CURRENT_USER, driversW, &hkey )) { DWORD count = sizeof(buffer); RegQueryValueExW( hkey, graphicsW, 0, NULL, (LPBYTE)buffer, &count ); RegCloseKey( hkey ); } } else lstrcpynW( buffer, driver, sizeof(buffer)/sizeof(WCHAR) ); name = buffer; while (name) { next = strchrW( name, ',' ); if (next) *next++ = 0; snprintfW( libname, sizeof(libname)/sizeof(WCHAR), drv_formatW, name ); if ((module = LoadLibraryW( libname )) != 0) break; switch (GetLastError()) { case ERROR_MOD_NOT_FOUND: strcpy( error, "The graphics driver is missing. Check your build!" ); break; case ERROR_DLL_INIT_FAILED: strcpy( error, "Make sure that your X server is running and that $DISPLAY is set correctly." ); break; default: sprintf( error, "Unknown error (%u).", GetLastError() ); break; } name = next; } if (module) { GetModuleFileNameW( module, buffer, MAX_PATH ); TRACE( "display %s driver %s\n", debugstr_guid(guid), debugstr_w(buffer) ); } sprintfW( key, device_keyW, guid->Data1, guid->Data2, guid->Data3, guid->Data4[0], guid->Data4[1], guid->Data4[2], guid->Data4[3], guid->Data4[4], guid->Data4[5], guid->Data4[6], guid->Data4[7] ); if (!RegCreateKeyExW( HKEY_LOCAL_MACHINE, key, 0, NULL, REG_OPTION_VOLATILE, KEY_SET_VALUE, NULL, &hkey, NULL )) { if (module) RegSetValueExW( hkey, graphics_driverW, 0, REG_SZ, (BYTE *)buffer, (strlenW(buffer) + 1) * sizeof(WCHAR) ); else RegSetValueExA( hkey, "DriverError", 0, REG_SZ, (BYTE *)error, strlen(error) + 1 ); RegCloseKey( hkey ); } return module; }
/* load a VxD and return a file handle to it */ HANDLE VXD_Open( LPCWSTR filenameW, DWORD access, SECURITY_ATTRIBUTES *sa ) { static const WCHAR dotVxDW[] = {'.','v','x','d',0}; int i; HANDLE handle; HMODULE module; WCHAR *p, name[16]; if (!(GetVersion() & 0x80000000)) /* there are no VxDs on NT */ { SetLastError( ERROR_FILE_NOT_FOUND ); return 0; } /* normalize the filename */ if (strlenW( filenameW ) >= sizeof(name)/sizeof(WCHAR) - 4 || strchrW( filenameW, '/' ) || strchrW( filenameW, '\\' )) { SetLastError( ERROR_FILE_NOT_FOUND ); return 0; } strcpyW( name, filenameW ); strlwrW( name ); p = strchrW( name, '.' ); if (!p) strcatW( name, dotVxDW ); else if (strcmpiW( p, dotVxDW )) /* existing extension has to be .vxd */ { SetLastError( ERROR_FILE_NOT_FOUND ); return 0; } /* try to load the module first */ if (!(module = LoadLibraryW( name ))) { FIXME( "Unknown/unsupported VxD %s. Try setting Windows version to 'nt40' or 'win31'.\n", debugstr_w(name) ); SetLastError( ERROR_FILE_NOT_FOUND ); return 0; } /* register the module in the global list if necessary */ RtlEnterCriticalSection( &vxd_section ); for (i = 0; i < MAX_VXD_MODULES; i++) { if (vxd_modules[i].module == module) { handle = vxd_modules[i].handle; goto done; /* already registered */ } if (!vxd_modules[i].module) /* new one, register it */ { IO_STATUS_BLOCK io; FILE_INTERNAL_INFORMATION info; /* get a file handle to the dummy file */ if (!(handle = open_vxd_handle( name ))) { FreeLibrary( module ); goto done; } if (!NtQueryInformationFile( handle, &io, &info, sizeof(info), FileInternalInformation )) vxd_modules[i].index = info.IndexNumber; vxd_modules[i].module = module; vxd_modules[i].handle = handle; vxd_modules[i].proc = (DeviceIoProc)GetProcAddress( module, "DeviceIoControl" ); goto done; } } ERR("too many open VxD modules, please report\n" ); FreeLibrary( module ); handle = 0; done: RtlLeaveCriticalSection( &vxd_section ); if (!DuplicateHandle( GetCurrentProcess(), handle, GetCurrentProcess(), &handle, 0, (sa && (sa->nLength>=sizeof(*sa)) && sa->bInheritHandle), DUP_HANDLE_SAME_ACCESS )) handle = 0; return handle; }
HRESULT __cdecl SchRpcRegisterTask(const WCHAR *path, const WCHAR *xml, DWORD flags, const WCHAR *sddl, DWORD task_logon_type, DWORD n_creds, const TASK_USER_CRED *creds, WCHAR **actual_path, TASK_XML_ERROR_INFO **xml_error_info) { WCHAR *full_name, *relative_path; DWORD disposition; HRESULT hr; TRACE("%s,%s,%#x,%s,%u,%u,%p,%p,%p\n", debugstr_w(path), debugstr_w(xml), flags, debugstr_w(sddl), task_logon_type, n_creds, creds, actual_path, xml_error_info); *actual_path = NULL; *xml_error_info = NULL; /* FIXME: assume that validation is performed on the client side */ if (flags & TASK_VALIDATE_ONLY) return S_OK; if (path) { full_name = get_full_name(path, &relative_path); if (!full_name) return E_OUTOFMEMORY; if (strchrW(path, '\\') || strchrW(path, '/')) { WCHAR *p = strrchrW(full_name, '/'); if (!p) p = strrchrW(full_name, '\\'); *p = 0; hr = create_directory(full_name); if (hr != S_OK && hr != HRESULT_FROM_WIN32(ERROR_ALREADY_EXISTS)) { heap_free(full_name); return hr; } *p = '\\'; } } else { IID iid; WCHAR uuid_str[39]; UuidCreate(&iid); StringFromGUID2(&iid, uuid_str, 39); full_name = get_full_name(uuid_str, &relative_path); if (!full_name) return E_OUTOFMEMORY; /* skip leading '\' */ relative_path++; } switch (flags & (TASK_CREATE | TASK_UPDATE)) { default: case TASK_CREATE: disposition = CREATE_NEW; break; case TASK_UPDATE: disposition = OPEN_EXISTING; break; case (TASK_CREATE | TASK_UPDATE): disposition = OPEN_ALWAYS; break; } hr = write_xml_utf8(full_name, disposition, xml); if (hr == S_OK) { *actual_path = heap_strdupW(relative_path); schedsvc_auto_start(); } heap_free(full_name); return hr; }
/***************************************************** * localmon_XcvDataPort [exported through MONITOREX] * * Execute command through a Communication-Channel * * PARAMS * hXcv [i] The Handle to work with * pszDataName [i] Name of the command to execute * pInputData [i] Buffer for extra Input Data (needed only for some commands) * cbInputData [i] Size in Bytes of Buffer at pInputData * pOutputData [o] Buffer to receive additional Data (needed only for some commands) * cbOutputData [i] Size in Bytes of Buffer at pOutputData * pcbOutputNeeded [o] PTR to receive the minimal Size in Bytes of the Buffer at pOutputData * * RETURNS * Success: ERROR_SUCCESS * Failure: win32 error code * * NOTES * * Minimal List of commands, that every Printmonitor DLL should support: * *| "MonitorUI" : Return the Name of the Userinterface-DLL as WSTR in pOutputData *| "AddPort" : Add a Port (Name as WSTR in pInputData) *| "DeletePort": Delete a Port (Name as WSTR in pInputData) * * */ static DWORD WINAPI localmon_XcvDataPort(HANDLE hXcv, LPCWSTR pszDataName, PBYTE pInputData, DWORD cbInputData, PBYTE pOutputData, DWORD cbOutputData, PDWORD pcbOutputNeeded) { WCHAR buffer[16]; /* buffer for a decimal number */ LPWSTR ptr; DWORD res; DWORD needed; HKEY hroot; TRACE("(%p, %s, %p, %d, %p, %d, %p)\n", hXcv, debugstr_w(pszDataName), pInputData, cbInputData, pOutputData, cbOutputData, pcbOutputNeeded); if (!lstrcmpW(pszDataName, cmd_AddPortW)) { TRACE("InputData (%d): %s\n", cbInputData, debugstr_w( (LPWSTR) pInputData)); res = RegOpenKeyW(HKEY_LOCAL_MACHINE, WinNT_CV_PortsW, &hroot); if (res == ERROR_SUCCESS) { if (does_port_exist((LPWSTR) pInputData)) { RegCloseKey(hroot); TRACE("=> %u\n", ERROR_ALREADY_EXISTS); return ERROR_ALREADY_EXISTS; } res = RegSetValueExW(hroot, (LPWSTR) pInputData, 0, REG_SZ, (const BYTE *) emptyW, sizeof(emptyW)); RegCloseKey(hroot); } TRACE("=> %u\n", res); return res; } if (!lstrcmpW(pszDataName, cmd_ConfigureLPTPortCommandOKW)) { TRACE("InputData (%d): %s\n", cbInputData, debugstr_w( (LPWSTR) pInputData)); res = RegCreateKeyW(HKEY_LOCAL_MACHINE, WinNT_CV_WindowsW, &hroot); if (res == ERROR_SUCCESS) { res = RegSetValueExW(hroot, TransmissionRetryTimeoutW, 0, REG_SZ, pInputData, cbInputData); RegCloseKey(hroot); } return res; } if (!lstrcmpW(pszDataName, cmd_DeletePortW)) { TRACE("InputData (%d): %s\n", cbInputData, debugstr_w( (LPWSTR) pInputData)); res = RegOpenKeyW(HKEY_LOCAL_MACHINE, WinNT_CV_PortsW, &hroot); if (res == ERROR_SUCCESS) { res = RegDeleteValueW(hroot, (LPWSTR) pInputData); RegCloseKey(hroot); TRACE("=> %u with %u\n", res, GetLastError() ); return res; } return ERROR_FILE_NOT_FOUND; } if (!lstrcmpW(pszDataName, cmd_GetDefaultCommConfigW)) { TRACE("InputData (%d): %s\n", cbInputData, debugstr_w( (LPWSTR) pInputData)); *pcbOutputNeeded = cbOutputData; res = GetDefaultCommConfigW((LPWSTR) pInputData, (LPCOMMCONFIG) pOutputData, pcbOutputNeeded); TRACE("got %u with %u\n", res, GetLastError() ); return res ? ERROR_SUCCESS : GetLastError(); } if (!lstrcmpW(pszDataName, cmd_GetTransmissionRetryTimeoutW)) { * pcbOutputNeeded = sizeof(DWORD); if (cbOutputData >= sizeof(DWORD)) { /* the w2k resource kit documented a default of 90, but that's wrong */ *((LPDWORD) pOutputData) = 45; res = RegOpenKeyW(HKEY_LOCAL_MACHINE, WinNT_CV_WindowsW, &hroot); if (res == ERROR_SUCCESS) { needed = sizeof(buffer) - sizeof(WCHAR); res = RegQueryValueExW(hroot, TransmissionRetryTimeoutW, NULL, NULL, (LPBYTE) buffer, &needed); if ((res == ERROR_SUCCESS) && (buffer[0])) { *((LPDWORD) pOutputData) = strtoulW(buffer, NULL, 0); } RegCloseKey(hroot); } return ERROR_SUCCESS; } return ERROR_INSUFFICIENT_BUFFER; } if (!lstrcmpW(pszDataName, cmd_MonitorUIW)) { * pcbOutputNeeded = sizeof(dllnameuiW); if (cbOutputData >= sizeof(dllnameuiW)) { memcpy(pOutputData, dllnameuiW, sizeof(dllnameuiW)); return ERROR_SUCCESS; } return ERROR_INSUFFICIENT_BUFFER; } if (!lstrcmpW(pszDataName, cmd_PortIsValidW)) { TRACE("InputData (%d): %s\n", cbInputData, debugstr_w( (LPWSTR) pInputData)); res = get_type_from_name((LPCWSTR) pInputData); TRACE("detected as %u\n", res); /* names, that we have recognized, are valid */ if (res) return ERROR_SUCCESS; /* ERROR_ACCESS_DENIED, ERROR_PATH_NOT_FOUND or something else */ TRACE("=> %u\n", GetLastError()); return GetLastError(); } if (!lstrcmpW(pszDataName, cmd_SetDefaultCommConfigW)) { /* get the portname from the Handle */ ptr = strchrW(((xcv_t *)hXcv)->nameW, ' '); if (ptr) { ptr++; /* skip the space */ } else { ptr = ((xcv_t *)hXcv)->nameW; } lstrcpynW(buffer, ptr, sizeof(buffer)/sizeof(WCHAR)); if (buffer[0]) buffer[lstrlenW(buffer)-1] = '\0'; /* remove the ':' */ res = SetDefaultCommConfigW(buffer, (LPCOMMCONFIG) pInputData, cbInputData); TRACE("got %u with %u\n", res, GetLastError() ); return res ? ERROR_SUCCESS : GetLastError(); } FIXME("command not supported: %s\n", debugstr_w(pszDataName)); return ERROR_INVALID_PARAMETER; }
static HRESULT WINAPI MkProtocol_StartEx(IInternetProtocolEx *iface, IUri *pUri, IInternetProtocolSink *pOIProtSink, IInternetBindInfo *pOIBindInfo, DWORD grfPI, HANDLE *dwReserved) { MkProtocol *This = impl_from_IInternetProtocolEx(iface); LPWSTR mime, progid, display_name, colon_ptr; DWORD path_size = INTERNET_MAX_URL_LENGTH; DWORD bindf=0, eaten=0, scheme=0, len; BSTR url, path_tmp, path = NULL; IParseDisplayName *pdn; BINDINFO bindinfo; STATSTG statstg; IMoniker *mon; HRESULT hres; CLSID clsid; TRACE("(%p)->(%p %p %p %08x %p)\n", This, pUri, pOIProtSink, pOIBindInfo, grfPI, dwReserved); hres = IUri_GetScheme(pUri, &scheme); if(FAILED(hres)) return hres; if(scheme != URL_SCHEME_MK) return INET_E_INVALID_URL; memset(&bindinfo, 0, sizeof(bindinfo)); bindinfo.cbSize = sizeof(BINDINFO); hres = IInternetBindInfo_GetBindInfo(pOIBindInfo, &bindf, &bindinfo); if(FAILED(hres)) { WARN("GetBindInfo failed: %08x\n", hres); return hres; } ReleaseBindInfo(&bindinfo); IInternetProtocolSink_ReportProgress(pOIProtSink, BINDSTATUS_SENDINGREQUEST, NULL); hres = IUri_GetDisplayUri(pUri, &url); if(FAILED(hres)) return hres; hres = FindMimeFromData(NULL, url, NULL, 0, NULL, 0, &mime, 0); SysFreeString(url); if(SUCCEEDED(hres)) { IInternetProtocolSink_ReportProgress(pOIProtSink, BINDSTATUS_MIMETYPEAVAILABLE, mime); CoTaskMemFree(mime); } hres = IUri_GetPath(pUri, &path_tmp); if(FAILED(hres)) return hres; path = heap_alloc(path_size); hres = UrlUnescapeW((LPWSTR)path_tmp, path, &path_size, 0); SysFreeString(path_tmp); if (FAILED(hres)) { heap_free(path); return report_result(pOIProtSink, INET_E_RESOURCE_NOT_FOUND, ERROR_INVALID_PARAMETER); } progid = path+1; /* skip '@' symbol */ colon_ptr = strchrW(path, ':'); if(!colon_ptr) { heap_free(path); return report_result(pOIProtSink, INET_E_RESOURCE_NOT_FOUND, ERROR_INVALID_PARAMETER); } len = strlenW(path); display_name = heap_alloc((len+1)*sizeof(WCHAR)); memcpy(display_name, path, (len+1)*sizeof(WCHAR)); progid[colon_ptr-progid] = 0; /* overwrite ':' with NULL terminator */ hres = CLSIDFromProgID(progid, &clsid); heap_free(path); if(FAILED(hres)) { heap_free(display_name); return report_result(pOIProtSink, INET_E_RESOURCE_NOT_FOUND, ERROR_INVALID_PARAMETER); } hres = CoCreateInstance(&clsid, NULL, CLSCTX_INPROC_SERVER|CLSCTX_INPROC_HANDLER, &IID_IParseDisplayName, (void**)&pdn); if(FAILED(hres)) { WARN("Could not create object %s\n", debugstr_guid(&clsid)); heap_free(display_name); return report_result(pOIProtSink, hres, ERROR_INVALID_PARAMETER); } hres = IParseDisplayName_ParseDisplayName(pdn, NULL /* FIXME */, display_name, &eaten, &mon); heap_free(display_name); IParseDisplayName_Release(pdn); if(FAILED(hres)) { WARN("ParseDisplayName failed: %08x\n", hres); return report_result(pOIProtSink, hres, ERROR_INVALID_PARAMETER); } if(This->stream) { IStream_Release(This->stream); This->stream = NULL; } hres = IMoniker_BindToStorage(mon, NULL /* FIXME */, NULL, &IID_IStream, (void**)&This->stream); IMoniker_Release(mon); if(FAILED(hres)) { WARN("BindToStorage failed: %08x\n", hres); return report_result(pOIProtSink, hres, ERROR_INVALID_PARAMETER); } hres = IStream_Stat(This->stream, &statstg, STATFLAG_NONAME); if(FAILED(hres)) { WARN("Stat failed: %08x\n", hres); return report_result(pOIProtSink, hres, ERROR_INVALID_PARAMETER); } IInternetProtocolSink_ReportData(pOIProtSink, BSCF_FIRSTDATANOTIFICATION | BSCF_LASTDATANOTIFICATION, statstg.cbSize.u.LowPart, statstg.cbSize.u.LowPart); return report_result(pOIProtSink, S_OK, ERROR_SUCCESS); }
static UINT search_reg( MSIPACKAGE *package, WCHAR **appValue, MSISIGNATURE *sig ) { static const WCHAR query[] = { 'S','E','L','E','C','T',' ','*',' ','F','R','O','M',' ', 'R','e','g','L','o','c','a','t','o','r',' ','W','H','E','R','E',' ', 'S','i','g','n','a','t','u','r','e','_',' ','=',' ', '\'','%','s','\'',0}; const WCHAR *keyPath, *valueName; WCHAR *deformatted = NULL, *ptr = NULL, *end; int root, type; REGSAM access = KEY_READ; HKEY rootKey, key = NULL; DWORD sz = 0, regType; LPBYTE value = NULL; MSIRECORD *row; UINT rc; TRACE("%s\n", debugstr_w(sig->Name)); *appValue = NULL; row = MSI_QueryGetRecord( package->db, query, sig->Name ); if (!row) { TRACE("failed to query RegLocator for %s\n", debugstr_w(sig->Name)); return ERROR_SUCCESS; } root = MSI_RecordGetInteger(row, 2); keyPath = MSI_RecordGetString(row, 3); valueName = MSI_RecordGetString(row, 4); type = MSI_RecordGetInteger(row, 5); deformat_string(package, keyPath, &deformatted); switch (root) { case msidbRegistryRootClassesRoot: rootKey = HKEY_CLASSES_ROOT; break; case msidbRegistryRootCurrentUser: rootKey = HKEY_CURRENT_USER; break; case msidbRegistryRootLocalMachine: rootKey = HKEY_LOCAL_MACHINE; if (type & msidbLocatorType64bit) access |= KEY_WOW64_64KEY; else access |= KEY_WOW64_32KEY; break; case msidbRegistryRootUsers: rootKey = HKEY_USERS; break; default: WARN("Unknown root key %d\n", root); goto end; } rc = RegOpenKeyExW( rootKey, deformatted, 0, access, &key ); if (rc) { TRACE("RegOpenKeyExW returned %d\n", rc); goto end; } msi_free(deformatted); deformat_string(package, valueName, &deformatted); rc = RegQueryValueExW(key, deformatted, NULL, NULL, NULL, &sz); if (rc) { TRACE("RegQueryValueExW returned %d\n", rc); goto end; } /* FIXME: sanity-check sz before allocating (is there an upper-limit * on the value of a property?) */ value = msi_alloc( sz ); rc = RegQueryValueExW(key, deformatted, NULL, ®Type, value, &sz); if (rc) { TRACE("RegQueryValueExW returned %d\n", rc); goto end; } /* bail out if the registry key is empty */ if (sz == 0) goto end; /* expand if needed */ if (regType == REG_EXPAND_SZ) { sz = ExpandEnvironmentStringsW((LPCWSTR)value, NULL, 0); if (sz) { LPWSTR buf = msi_alloc(sz * sizeof(WCHAR)); ExpandEnvironmentStringsW((LPCWSTR)value, buf, sz); msi_free(value); value = (LPBYTE)buf; } } if ((regType == REG_SZ || regType == REG_EXPAND_SZ) && (ptr = strchrW((LPWSTR)value, '"')) && (end = strchrW(++ptr, '"'))) *end = '\0'; else ptr = (LPWSTR)value; switch (type & 0x0f) { case msidbLocatorTypeDirectory: search_directory( package, sig, ptr, 0, appValue ); break; case msidbLocatorTypeFileName: *appValue = search_file( package, ptr, sig ); break; case msidbLocatorTypeRawValue: convert_reg_value( regType, value, sz, appValue ); break; default: FIXME("unimplemented for type %d (key path %s, value %s)\n", type, debugstr_w(keyPath), debugstr_w(valueName)); } end: msi_free( value ); RegCloseKey( key ); msi_free( deformatted ); msiobj_release(&row->hdr); return ERROR_SUCCESS; }
static HRESULT WINAPI FileProtocol_StartEx(IInternetProtocolEx *iface, IUri *pUri, IInternetProtocolSink *pOIProtSink, IInternetBindInfo *pOIBindInfo, DWORD grfPI, HANDLE *dwReserved) { FileProtocol *This = impl_from_IInternetProtocolEx(iface); WCHAR path[MAX_PATH], *ptr; LARGE_INTEGER file_size; HANDLE file_handle; BINDINFO bindinfo; DWORD grfBINDF = 0; DWORD scheme, size; LPWSTR mime = NULL; WCHAR null_char = 0; BSTR ext; HRESULT hres; TRACE("(%p)->(%p %p %p %08x %p)\n", This, pUri, pOIProtSink, pOIBindInfo, grfPI, dwReserved); if(!pUri) return E_INVALIDARG; scheme = 0; hres = IUri_GetScheme(pUri, &scheme); if(FAILED(hres)) return hres; if(scheme != URL_SCHEME_FILE) return E_INVALIDARG; memset(&bindinfo, 0, sizeof(bindinfo)); bindinfo.cbSize = sizeof(BINDINFO); hres = IInternetBindInfo_GetBindInfo(pOIBindInfo, &grfBINDF, &bindinfo); if(FAILED(hres)) { WARN("GetBindInfo failed: %08x\n", hres); return hres; } ReleaseBindInfo(&bindinfo); if(!(grfBINDF & BINDF_FROMURLMON)) IInternetProtocolSink_ReportProgress(pOIProtSink, BINDSTATUS_DIRECTBIND, NULL); if(This->file != INVALID_HANDLE_VALUE) { IInternetProtocolSink_ReportData(pOIProtSink, BSCF_FIRSTDATANOTIFICATION|BSCF_LASTDATANOTIFICATION, This->size, This->size); return S_OK; } IInternetProtocolSink_ReportProgress(pOIProtSink, BINDSTATUS_SENDINGREQUEST, &null_char); size = 0; hres = CoInternetParseIUri(pUri, PARSE_PATH_FROM_URL, 0, path, sizeof(path)/sizeof(WCHAR), &size, 0); if(FAILED(hres)) { WARN("CoInternetParseIUri failed: %08x\n", hres); return report_result(pOIProtSink, hres, 0); } file_handle = CreateFileW(path, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL); if(file_handle == INVALID_HANDLE_VALUE && (ptr = strrchrW(path, '#'))) { /* If path contains fragment part, try without it. */ *ptr = 0; file_handle = CreateFileW(path, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL); } if(file_handle == INVALID_HANDLE_VALUE) return report_result(pOIProtSink, INET_E_RESOURCE_NOT_FOUND, GetLastError()); if(!GetFileSizeEx(file_handle, &file_size)) { CloseHandle(file_handle); return report_result(pOIProtSink, INET_E_RESOURCE_NOT_FOUND, GetLastError()); } This->file = file_handle; This->size = file_size.u.LowPart; IInternetProtocolSink_ReportProgress(pOIProtSink, BINDSTATUS_CACHEFILENAMEAVAILABLE, path); hres = IUri_GetExtension(pUri, &ext); if(SUCCEEDED(hres)) { if(hres == S_OK && *ext) { if((ptr = strchrW(ext, '#'))) *ptr = 0; hres = find_mime_from_ext(ext, &mime); if(SUCCEEDED(hres)) { IInternetProtocolSink_ReportProgress(pOIProtSink, (grfBINDF & BINDF_FROMURLMON) ? BINDSTATUS_VERIFIEDMIMETYPEAVAILABLE : BINDSTATUS_MIMETYPEAVAILABLE, mime); CoTaskMemFree(mime); } } SysFreeString(ext); } IInternetProtocolSink_ReportData(pOIProtSink, BSCF_FIRSTDATANOTIFICATION|BSCF_LASTDATANOTIFICATION, This->size, This->size); return report_result(pOIProtSink, S_OK, 0); }
/* loads the LDIDs specified in the install section of an INF */ void set_ldids(HINF hInf, LPCWSTR pszInstallSection, LPCWSTR pszWorkingDir) { WCHAR field[MAX_FIELD_LENGTH]; WCHAR line[MAX_FIELD_LENGTH]; WCHAR dest[MAX_PATH]; INFCONTEXT context; DWORD size; int ldid; static const WCHAR source_dir[] = {'S','o','u','r','c','e','D','i','r',0}; static const WCHAR custDestW[] = { 'C','u','s','t','o','m','D','e','s','t','i','n','a','t','i','o','n',0 }; if (!SetupGetLineTextW(NULL, hInf, pszInstallSection, custDestW, field, MAX_FIELD_LENGTH, &size)) return; if (!SetupFindFirstLineW(hInf, field, NULL, &context)) return; do { LPWSTR value, ptr, key, key_copy = NULL; DWORD flags = 0; SetupGetLineTextW(&context, NULL, NULL, NULL, line, MAX_FIELD_LENGTH, &size); /* SetupGetLineTextW returns the value if there is only one key, but * returns the whole line if there is more than one key */ if (!(value = strchrW(line, '='))) { SetupGetStringFieldW(&context, 0, NULL, 0, &size); key = HeapAlloc(GetProcessHeap(), 0, size * sizeof(WCHAR)); key_copy = key; SetupGetStringFieldW(&context, 0, key, size, &size); value = line; } else { key = line; *(value++) = '\0'; } /* remove leading whitespace from the value */ while (*value == ' ') value++; /* Extract the flags */ ptr = strchrW(value, ','); if (ptr) { *ptr = '\0'; flags = atolW(ptr+1); } /* set dest to pszWorkingDir if key is SourceDir */ if (pszWorkingDir && !lstrcmpiW(value, source_dir)) lstrcpynW(dest, pszWorkingDir, MAX_PATH); else get_dest_dir(hInf, value, dest, MAX_PATH); /* If prompting required, provide dialog to request path */ if (flags & 0x04) FIXME("Need to support changing paths - default will be used\n"); /* set all ldids to dest */ while ((ptr = get_parameter(&key, ','))) { ldid = atolW(ptr); SetupSetDirectoryIdW(hInf, ldid, dest); } HeapFree(GetProcessHeap(), 0, key_copy); } while (SetupFindNextLine(&context, &context)); }
BOOL path_find_symbol_file(const struct process* pcs, const struct module* module, PCSTR full_path, const GUID* guid, DWORD dw1, DWORD dw2, PSTR buffer, BOOL* is_unmatched) { struct module_find mf; WCHAR full_pathW[MAX_PATH]; WCHAR tmp[MAX_PATH]; WCHAR* ptr; const WCHAR* filename; WCHAR* searchPath = pcs->search_path; TRACE("(pcs = %p, full_path = %s, guid = %s, dw1 = 0x%08x, dw2 = 0x%08x, buffer = %p)\n", pcs, debugstr_a(full_path), debugstr_guid(guid), dw1, dw2, buffer); mf.guid = guid; mf.dw1 = dw1; mf.dw2 = dw2; mf.matched = 0; MultiByteToWideChar(CP_ACP, 0, full_path, -1, full_pathW, MAX_PATH); filename = file_nameW(full_pathW); mf.kind = module_get_type_by_name(filename); *is_unmatched = FALSE; /* first check full path to file */ if (module_find_cb(full_pathW, &mf)) { WideCharToMultiByte(CP_ACP, 0, full_pathW, -1, buffer, MAX_PATH, NULL, NULL); return TRUE; } /* FIXME: Use Environment-Variables (see MS docs) _NT_SYMBOL_PATH and _NT_ALT_SYMBOL_PATH FIXME: Implement "Standard Path Elements" (Path) ... (see MS docs) do a search for (every?) path-element like this ... <path> <path>\dll <path>\symbols\dll (dll may be exe, or sys depending on the file extension) */ /* 2. check module-path */ file_pathW(module->module.LoadedImageName, tmp); if (do_searchW(filename, tmp, FALSE, module_find_cb, &mf)) { WideCharToMultiByte(CP_ACP, 0, tmp, -1, buffer, MAX_PATH, NULL, NULL); return TRUE; } /* 3. check search-path */ while (searchPath) { ptr = strchrW(searchPath, ';'); if (ptr) { memcpy(tmp, searchPath, (ptr - searchPath) * sizeof(WCHAR)); tmp[ptr - searchPath] = '\0'; searchPath = ptr + 1; } else { strcpyW(tmp, searchPath); searchPath = NULL; } if (do_searchW(filename, tmp, FALSE, module_find_cb, &mf)) { /* return first fully matched file */ WideCharToMultiByte(CP_ACP, 0, tmp, -1, buffer, MAX_PATH, NULL, NULL); return TRUE; } } /* if no fully matching file is found, return the best matching file if any */ if ((dbghelp_options & SYMOPT_LOAD_ANYTHING) && mf.matched) { WideCharToMultiByte(CP_ACP, 0, mf.filename, -1, buffer, MAX_PATH, NULL, NULL); *is_unmatched = TRUE; return TRUE; } return FALSE; }
/**************************************************************************** * WCMD_HandleTildaModifiers * * Handle the ~ modifiers when expanding %0-9 or (%a-z in for command) * %~xxxxxV (V=0-9 or A-Z) * Where xxxx is any combination of: * ~ - Removes quotes * f - Fully qualified path (assumes current dir if not drive\dir) * d - drive letter * p - path * n - filename * x - file extension * s - path with shortnames * a - attributes * t - date/time * z - size * $ENVVAR: - Searches ENVVAR for (contents of V) and expands to fully * qualified path * * To work out the length of the modifier: * * Note: In the case of %0-9 knowing the end of the modifier is easy, * but in a for loop, the for end WCHARacter may also be a modifier * eg. for %a in (c:\a.a) do echo XXX * where XXX = %~a (just ~) * %~aa (~ and attributes) * %~aaxa (~, attributes and extension) * BUT %~aax (~ and attributes followed by 'x') * * Hence search forwards until find an invalid modifier, and then * backwards until find for variable or 0-9 */ void WCMD_HandleTildaModifiers(WCHAR **start, const WCHAR *forVariable, const WCHAR *forValue, BOOL justFors) { #define NUMMODIFIERS 11 static const WCHAR validmodifiers[NUMMODIFIERS] = { '~', 'f', 'd', 'p', 'n', 'x', 's', 'a', 't', 'z', '$' }; static const WCHAR space[] = {' ', '\0'}; WIN32_FILE_ATTRIBUTE_DATA fileInfo; WCHAR outputparam[MAX_PATH]; WCHAR finaloutput[MAX_PATH]; WCHAR fullfilename[MAX_PATH]; WCHAR thisoutput[MAX_PATH]; WCHAR *pos = *start+1; WCHAR *firstModifier = pos; WCHAR *lastModifier = NULL; int modifierLen = 0; BOOL finished = FALSE; int i = 0; BOOL exists = TRUE; BOOL skipFileParsing = FALSE; BOOL doneModifier = FALSE; /* Search forwards until find invalid character modifier */ while (!finished) { /* Work on the previous character */ if (lastModifier != NULL) { for (i=0; i<NUMMODIFIERS; i++) { if (validmodifiers[i] == *lastModifier) { /* Special case '$' to skip until : found */ if (*lastModifier == '$') { while (*pos != ':' && *pos) pos++; if (*pos == 0x00) return; /* Invalid syntax */ pos++; /* Skip ':' */ } break; } } if (i==NUMMODIFIERS) { finished = TRUE; } } /* Save this one away */ if (!finished) { lastModifier = pos; pos++; } } while (lastModifier > firstModifier) { WINE_TRACE("Looking backwards for parameter id: %s / %s\n", wine_dbgstr_w(lastModifier), wine_dbgstr_w(forVariable)); if (!justFors && context && (*lastModifier >= '0' && *lastModifier <= '9')) { /* Its a valid parameter identifier - OK */ break; } else if (forVariable && *lastModifier == *(forVariable+1)) { /* Its a valid parameter identifier - OK */ break; } else { lastModifier--; } } if (lastModifier == firstModifier) return; /* Invalid syntax */ /* Extract the parameter to play with */ if (*lastModifier == '0') { strcpyW(outputparam, context->batchfileW); } else if ((*lastModifier >= '1' && *lastModifier <= '9')) { strcpyW(outputparam, WCMD_parameter (context -> command, *lastModifier-'0' + context -> shift_count[*lastModifier-'0'], NULL, NULL)); } else { strcpyW(outputparam, forValue); } /* So now, firstModifier points to beginning of modifiers, lastModifier points to the variable just after the modifiers. Process modifiers in a specific order, remembering there could be duplicates */ modifierLen = lastModifier - firstModifier; finaloutput[0] = 0x00; /* Useful for debugging purposes: */ /*printf("Modifier string '%*.*s' and variable is %c\n Param starts as '%s'\n", (modifierLen), (modifierLen), firstModifier, *lastModifier, outputparam);*/ /* 1. Handle '~' : Strip surrounding quotes */ if (outputparam[0]=='"' && memchrW(firstModifier, '~', modifierLen) != NULL) { int len = strlenW(outputparam); if (outputparam[len-1] == '"') { outputparam[len-1]=0x00; len = len - 1; } memmove(outputparam, &outputparam[1], (len * sizeof(WCHAR))-1); } /* 2. Handle the special case of a $ */ if (memchrW(firstModifier, '$', modifierLen) != NULL) { /* Special Case: Search envar specified in $[envvar] for outputparam Note both $ and : are guaranteed otherwise check above would fail */ WCHAR *begin = strchrW(firstModifier, '$') + 1; WCHAR *end = strchrW(firstModifier, ':'); WCHAR env[MAX_PATH]; WCHAR fullpath[MAX_PATH]; /* Extract the env var */ memcpy(env, begin, (end-begin) * sizeof(WCHAR)); env[(end-begin)] = 0x00; /* If env var not found, return empty string */ if ((GetEnvironmentVariableW(env, fullpath, MAX_PATH) == 0) || (SearchPathW(fullpath, outputparam, NULL, MAX_PATH, outputparam, NULL) == 0)) { finaloutput[0] = 0x00; outputparam[0] = 0x00; skipFileParsing = TRUE; } } /* After this, we need full information on the file, which is valid not to exist. */ if (!skipFileParsing) { if (GetFullPathNameW(outputparam, MAX_PATH, fullfilename, NULL) == 0) return; exists = GetFileAttributesExW(fullfilename, GetFileExInfoStandard, &fileInfo); /* 2. Handle 'a' : Output attributes */ if (exists && memchrW(firstModifier, 'a', modifierLen) != NULL) { WCHAR defaults[] = {'-','-','-','-','-','-','-','-','-','\0'}; doneModifier = TRUE; strcpyW(thisoutput, defaults); if (fileInfo.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) thisoutput[0]='d'; if (fileInfo.dwFileAttributes & FILE_ATTRIBUTE_READONLY) thisoutput[1]='r'; if (fileInfo.dwFileAttributes & FILE_ATTRIBUTE_ARCHIVE) thisoutput[2]='a'; if (fileInfo.dwFileAttributes & FILE_ATTRIBUTE_HIDDEN) thisoutput[3]='h'; if (fileInfo.dwFileAttributes & FILE_ATTRIBUTE_SYSTEM) thisoutput[4]='s'; if (fileInfo.dwFileAttributes & FILE_ATTRIBUTE_COMPRESSED) thisoutput[5]='c'; /* FIXME: What are 6 and 7? */ if (fileInfo.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) thisoutput[8]='l'; strcatW(finaloutput, thisoutput); } /* 3. Handle 't' : Date+time */ if (exists && memchrW(firstModifier, 't', modifierLen) != NULL) { SYSTEMTIME systime; int datelen; doneModifier = TRUE; if (finaloutput[0] != 0x00) strcatW(finaloutput, space); /* Format the time */ FileTimeToSystemTime(&fileInfo.ftLastWriteTime, &systime); GetDateFormatW(LOCALE_USER_DEFAULT, DATE_SHORTDATE, &systime, NULL, thisoutput, MAX_PATH); strcatW(thisoutput, space); datelen = strlenW(thisoutput); GetTimeFormatW(LOCALE_USER_DEFAULT, TIME_NOSECONDS, &systime, NULL, (thisoutput+datelen), MAX_PATH-datelen); strcatW(finaloutput, thisoutput); } /* 4. Handle 'z' : File length */ if (exists && memchrW(firstModifier, 'z', modifierLen) != NULL) { /* FIXME: Output full 64 bit size (sprintf does not support I64 here) */ ULONG/*64*/ fullsize = /*(fileInfo.nFileSizeHigh << 32) +*/ fileInfo.nFileSizeLow; static const WCHAR fmt[] = {'%','u','\0'}; doneModifier = TRUE; if (finaloutput[0] != 0x00) strcatW(finaloutput, space); wsprintfW(thisoutput, fmt, fullsize); strcatW(finaloutput, thisoutput); } /* 4. Handle 's' : Use short paths (File doesn't have to exist) */ if (memchrW(firstModifier, 's', modifierLen) != NULL) { if (finaloutput[0] != 0x00) strcatW(finaloutput, space); /* Don't flag as doneModifier - %~s on its own is processed later */ GetShortPathNameW(outputparam, outputparam, sizeof(outputparam)/sizeof(outputparam[0])); } /* 5. Handle 'f' : Fully qualified path (File doesn't have to exist) */ /* Note this overrides d,p,n,x */ if (memchrW(firstModifier, 'f', modifierLen) != NULL) { doneModifier = TRUE; if (finaloutput[0] != 0x00) strcatW(finaloutput, space); strcatW(finaloutput, fullfilename); } else { WCHAR drive[10]; WCHAR dir[MAX_PATH]; WCHAR fname[MAX_PATH]; WCHAR ext[MAX_PATH]; BOOL doneFileModifier = FALSE; if (finaloutput[0] != 0x00) strcatW(finaloutput, space); /* Split into components */ WCMD_splitpath(fullfilename, drive, dir, fname, ext); /* 5. Handle 'd' : Drive Letter */ if (memchrW(firstModifier, 'd', modifierLen) != NULL) { strcatW(finaloutput, drive); doneModifier = TRUE; doneFileModifier = TRUE; } /* 6. Handle 'p' : Path */ if (memchrW(firstModifier, 'p', modifierLen) != NULL) { strcatW(finaloutput, dir); doneModifier = TRUE; doneFileModifier = TRUE; } /* 7. Handle 'n' : Name */ if (memchrW(firstModifier, 'n', modifierLen) != NULL) { strcatW(finaloutput, fname); doneModifier = TRUE; doneFileModifier = TRUE; } /* 8. Handle 'x' : Ext */ if (memchrW(firstModifier, 'x', modifierLen) != NULL) { strcatW(finaloutput, ext); doneModifier = TRUE; doneFileModifier = TRUE; } /* If 's' but no other parameter, dump the whole thing */ if (!doneFileModifier && memchrW(firstModifier, 's', modifierLen) != NULL) { doneModifier = TRUE; if (finaloutput[0] != 0x00) strcatW(finaloutput, space); strcatW(finaloutput, outputparam); } } } /* If No other modifier processed, just add in parameter */ if (!doneModifier) strcpyW(finaloutput, outputparam); /* Finish by inserting the replacement into the string */ WCMD_strsubstW(*start, lastModifier+1, finaloutput, -1); }
/* ################################ */ static BOOL parse_rundll(context_t * cx) { LPWSTR ptr; DWORD index; WCHAR txtW[2]; WCHAR c; c = get_next_wchar(cx, TRUE); txtW[1] = '\0'; while (c) { while ( (c == ' ') || (c == '\t')) { c = get_next_wchar(cx, TRUE); } txtW[0] = c; if (c == '@') { /* read commands from a File */ ptr = get_next_wstr(cx); FIXME("redir not supported: %s\n", debugstr_w(ptr)); return FALSE; } else if (c == '/') { c = get_next_wchar(cx, FALSE); while ( c ) { txtW[0] = c; ptr = strchrW(optionsW, c); if (ptr) { index = ptr - optionsW; cx->options[index] = get_next_wstr(cx); TRACE(" opt: %s %s\n", debugstr_w(txtW), debugstr_w(cx->options[index])); c = 0; } else { ptr = strchrW(flagsW, c); if (ptr) { index = ptr - flagsW; cx->flags[index] = TRUE; TRACE("flag: %s\n", debugstr_w(txtW)); } else { cx->command = c; cx->subcommand = '\0'; TRACE(" cmd: %s\n", debugstr_w(txtW)); } /* help has priority over all commands */ if (c == '?') { return TRUE; } c = get_next_wchar(cx, FALSE); /* Some commands use two wchar */ if ((cx->command == 'd') || (cx->command == 'g') || (cx->command == 'i') || (cx->command == 'S') || (cx->command == 'X') ){ cx->subcommand = c; txtW[0] = c; TRACE(" sub: %s\n", debugstr_w(txtW)); c = get_next_wchar(cx, FALSE); } } } c = get_next_wchar(cx, TRUE); } else { /* The commands 'S' and 'X' have additional Parameter */ if ((cx->command == 'S') || (cx->command == 'X')) { /* the actual WCHAR is the start from the extra Parameter */ cx->pNextCharW--; TRACE("%d extra Parameter, starting with %s\n", 1 + (cx->argc - cx->next_arg), debugstr_w(cx->pNextCharW)); return TRUE; } FIXME("0x%x: %s is unknown\n", c, debugstr_wn(&c, 1)); return FALSE; } } return TRUE; }
HRESULT create_monodata(REFIID riid, LPVOID *ppObj ) { static const WCHAR wszAssembly[] = {'A','s','s','e','m','b','l','y',0}; static const WCHAR wszCodebase[] = {'C','o','d','e','B','a','s','e',0}; static const WCHAR wszClass[] = {'C','l','a','s','s',0}; static const WCHAR wszFileSlash[] = {'f','i','l','e',':','/','/','/',0}; static const WCHAR wszCLSIDSlash[] = {'C','L','S','I','D','\\',0}; static const WCHAR wszInprocServer32[] = {'\\','I','n','p','r','o','c','S','e','r','v','e','r','3','2',0}; static const WCHAR wszDLL[] = {'.','d','l','l',0}; WCHAR path[CHARS_IN_GUID + ARRAYSIZE(wszCLSIDSlash) + ARRAYSIZE(wszInprocServer32) - 1]; MonoDomain *domain; MonoAssembly *assembly; ICLRRuntimeInfo *info = NULL; RuntimeHost *host; HRESULT hr; HKEY key, subkey; LONG res; int offset = 0; DWORD numKeys, keyLength; WCHAR codebase[MAX_PATH + 8]; WCHAR classname[350], subkeyName[256]; WCHAR filename[MAX_PATH]; DWORD dwBufLen = 350; lstrcpyW(path, wszCLSIDSlash); StringFromGUID2(riid, path + lstrlenW(wszCLSIDSlash), CHARS_IN_GUID); lstrcatW(path, wszInprocServer32); TRACE("Registry key: %s\n", debugstr_w(path)); res = RegOpenKeyExW(HKEY_CLASSES_ROOT, path, 0, KEY_READ, &key); if (res == ERROR_FILE_NOT_FOUND) return CLASS_E_CLASSNOTAVAILABLE; res = RegGetValueW( key, NULL, wszClass, RRF_RT_REG_SZ, NULL, classname, &dwBufLen); if(res != ERROR_SUCCESS) { WARN("Class value cannot be found.\n"); hr = CLASS_E_CLASSNOTAVAILABLE; goto cleanup; } TRACE("classname (%s)\n", debugstr_w(classname)); dwBufLen = MAX_PATH + 8; res = RegGetValueW( key, NULL, wszCodebase, RRF_RT_REG_SZ, NULL, codebase, &dwBufLen); if(res == ERROR_SUCCESS) { /* Strip file:/// */ if(strncmpW(codebase, wszFileSlash, strlenW(wszFileSlash)) == 0) offset = strlenW(wszFileSlash); strcpyW(filename, codebase + offset); } else { WCHAR assemblyname[MAX_PATH + 8]; hr = CLASS_E_CLASSNOTAVAILABLE; WARN("CodeBase value cannot be found, trying Assembly.\n"); /* get the last subkey of InprocServer32 */ res = RegQueryInfoKeyW(key, 0, 0, 0, &numKeys, 0, 0, 0, 0, 0, 0, 0); if (res != ERROR_SUCCESS || numKeys == 0) goto cleanup; numKeys--; keyLength = sizeof(subkeyName) / sizeof(WCHAR); res = RegEnumKeyExW(key, numKeys, subkeyName, &keyLength, 0, 0, 0, 0); if (res != ERROR_SUCCESS) goto cleanup; res = RegOpenKeyExW(key, subkeyName, 0, KEY_READ, &subkey); if (res != ERROR_SUCCESS) goto cleanup; dwBufLen = MAX_PATH + 8; res = RegGetValueW(subkey, NULL, wszAssembly, RRF_RT_REG_SZ, NULL, assemblyname, &dwBufLen); RegCloseKey(subkey); if (res != ERROR_SUCCESS) goto cleanup; hr = get_file_from_strongname(assemblyname, filename, MAX_PATH); if (!SUCCEEDED(hr)) { /* * The registry doesn't have a CodeBase entry and it's not in the GAC. * * Use the Assembly Key to retrieve the filename. * Assembly : REG_SZ : AssemblyName, Version=X.X.X.X, Culture=neutral, PublicKeyToken=null */ WCHAR *ns; WARN("Attempt to load from the application directory.\n"); GetModuleFileNameW(NULL, filename, MAX_PATH); ns = strrchrW(filename, '\\'); *(ns+1) = '\0'; ns = strchrW(assemblyname, ','); *(ns) = '\0'; strcatW(filename, assemblyname); *(ns) = '.'; strcatW(filename, wszDLL); } } TRACE("filename (%s)\n", debugstr_w(filename)); *ppObj = NULL; hr = get_runtime_info(filename, NULL, NULL, 0, 0, FALSE, &info); if (SUCCEEDED(hr)) { hr = ICLRRuntimeInfo_GetRuntimeHost(info, &host); if (SUCCEEDED(hr)) hr = RuntimeHost_GetDefaultDomain(host, &domain); if (SUCCEEDED(hr)) { MonoImage *image; MonoClass *klass; MonoObject *result; IUnknown *unk = NULL; char *filenameA, *ns; char *classA; hr = CLASS_E_CLASSNOTAVAILABLE; mono_thread_attach(domain); filenameA = WtoA(filename); assembly = mono_domain_assembly_open(domain, filenameA); HeapFree(GetProcessHeap(), 0, filenameA); if (!assembly) { ERR("Cannot open assembly %s\n", filenameA); goto cleanup; } image = mono_assembly_get_image(assembly); if (!image) { ERR("Couldn't get assembly image\n"); goto cleanup; } classA = WtoA(classname); ns = strrchr(classA, '.'); *ns = '\0'; klass = mono_class_from_name(image, classA, ns+1); HeapFree(GetProcessHeap(), 0, classA); if (!klass) { ERR("Couldn't get class from image\n"); goto cleanup; } /* * Use the default constructor for the .NET class. */ result = mono_object_new(domain, klass); mono_runtime_object_init(result); hr = RuntimeHost_GetIUnknownForObject(host, result, &unk); if (SUCCEEDED(hr)) { hr = IUnknown_QueryInterface(unk, &IID_IUnknown, ppObj); IUnknown_Release(unk); } else hr = CLASS_E_CLASSNOTAVAILABLE; } else hr = CLASS_E_CLASSNOTAVAILABLE; } else hr = CLASS_E_CLASSNOTAVAILABLE; cleanup: if(info) ICLRRuntimeInfo_Release(info); RegCloseKey(key); return hr; }
/************************************************************************** * DRIVER_TryOpenDriver32 [internal] * * Tries to load a 32 bit driver whose DLL's (module) name is fn */ LPWINE_DRIVER DRIVER_TryOpenDriver32(LPCWSTR fn, LPARAM lParam2) { LPWINE_DRIVER lpDrv = NULL; HMODULE hModule = 0; LPWSTR ptr; LPCSTR cause = 0; TRACE("(%s, %08lX);\n", debugstr_w(fn), lParam2); if ((ptr = strchrW(fn, ' ')) != NULL) { *ptr++ = '\0'; while (*ptr == ' ') ptr++; if (*ptr == '\0') ptr = NULL; } lpDrv = HeapAlloc(GetProcessHeap(), 0, sizeof(WINE_DRIVER)); if (lpDrv == NULL) { cause = "OOM"; goto exit; } if ((hModule = LoadLibraryW(fn)) == 0) { cause = "Not a 32 bit lib"; goto exit; } lpDrv->lpDrvProc = (DRIVERPROC)GetProcAddress(hModule, "DriverProc"); if (lpDrv->lpDrvProc == NULL) { cause = "no DriverProc"; goto exit; } lpDrv->dwFlags = 0; lpDrv->hModule = hModule; lpDrv->dwDriverID = 0; /* Win32 installable drivers must support a two phase opening scheme: * + first open with NULL as lParam2 (session instance), * + then do a second open with the real non null lParam2) */ if (DRIVER_GetNumberOfModuleRefs(lpDrv->hModule, NULL) == 0 && lParam2) { LPWINE_DRIVER ret; if (!DRIVER_AddToList(lpDrv, (LPARAM)ptr, 0L)) { cause = "load0 failed"; goto exit; } ret = DRIVER_TryOpenDriver32(fn, lParam2); if (!ret) { CloseDriver((HDRVR)lpDrv, 0L, 0L); cause = "load1 failed"; goto exit; } return ret; } if (!DRIVER_AddToList(lpDrv, (LPARAM)ptr, lParam2)) { cause = "load failed"; goto exit; } TRACE("=> %p\n", lpDrv); return lpDrv; exit: FreeLibrary(hModule); HeapFree(GetProcessHeap(), 0, lpDrv); TRACE("Unable to load 32 bit module %s: %s\n", debugstr_w(fn), cause); return NULL; }
static inline HRESULT handle_xml_load(BindStatusCallback *This) { static const WCHAR selectW[] = {'p','r','o','c','e','s','s','i','n','g','-', 'i','n','s','t','r','u','c','t','i','o','n','(','\'','x','m','l', '-','s','t','y','l','e','s','h','e','e','t','\'',')',0}; static const WCHAR hrefW[] = {'h','r','e','f','=',0}; IXMLDOMDocument3 *xml = NULL, *xsl = NULL; IXMLDOMNode *stylesheet; IBindCtx *pbc; IMoniker *mon; LPOLESTR xsl_url; LARGE_INTEGER off; VARIANT_BOOL succ; VARIANT var; WCHAR *href = NULL, *p; BSTR bstr; HRESULT hres; off.QuadPart = 0; hres = IStream_Seek(This->stream, off, STREAM_SEEK_SET, NULL); if(FAILED(hres)) return display_error_page(This); hres = DOMDocument_create(MSXML_DEFAULT, (void**)&xml); if(FAILED(hres)) return display_error_page(This); V_VT(&var) = VT_UNKNOWN; V_UNKNOWN(&var) = (IUnknown*)This->stream; hres = IXMLDOMDocument3_load(xml, var, &succ); if(FAILED(hres) || !succ) { IXMLDOMDocument3_Release(xml); return display_error_page(This); } V_VT(&var) = VT_EMPTY; bstr = SysAllocString(selectW); hres = IXMLDOMDocument3_selectSingleNode(xml, bstr, &stylesheet); SysFreeString(bstr); if(hres != S_OK) { IXMLDOMDocument3_Release(xml); return display_error_page(This); } hres = IXMLDOMNode_get_nodeValue(stylesheet, &var); IXMLDOMNode_Release(stylesheet); if(SUCCEEDED(hres) && V_VT(&var)!=VT_BSTR) { FIXME("Variant type %d not supported\n", V_VT(&var)); VariantClear(&var); hres = E_FAIL; } if(FAILED(hres)) { IXMLDOMDocument3_Release(xml); return display_error_page(This); } /* TODO: fix parsing processing instruction value */ if((p = strstrW(V_BSTR(&var), hrefW))) { p += ARRAY_SIZE(hrefW) - 1; if(*p!='\'' && *p!='\"') p = NULL; else { href = p+1; p = strchrW(href, *p); } } if(p) { *p = 0; } else { VariantClear(&var); IXMLDOMDocument3_Release(xml); return display_error_page(This); } hres = CreateURLMonikerEx(This->mon, href, &mon, 0); VariantClear(&var); if(FAILED(hres)) { IXMLDOMDocument3_Release(xml); return display_error_page(This); } hres = CreateBindCtx(0, &pbc); if(SUCCEEDED(hres)) { hres = IMoniker_GetDisplayName(mon, pbc, NULL, &xsl_url); IMoniker_Release(mon); IBindCtx_Release(pbc); } if(FAILED(hres)) { IXMLDOMDocument3_Release(xml); return display_error_page(This); } V_VT(&var) = VT_BSTR; V_BSTR(&var) = SysAllocString(xsl_url); CoTaskMemFree(xsl_url); if(!V_BSTR(&var)) { IXMLDOMDocument3_Release(xml); return display_error_page(This); } hres = DOMDocument_create(MSXML_DEFAULT, (void**)&xsl); if(FAILED(hres)) { VariantClear(&var); IXMLDOMDocument3_Release(xml); return display_error_page(This); } /* TODO: do the binding asynchronously */ hres = IXMLDOMDocument3_load(xsl, var, &succ); VariantClear(&var); if(FAILED(hres) || !succ) { IXMLDOMDocument3_Release(xsl); IXMLDOMDocument3_Release(xml); return display_error_page(This); } hres = IXMLDOMDocument3_transformNode(xml, (IXMLDOMNode*)xsl, &bstr); IXMLDOMDocument3_Release(xsl); IXMLDOMDocument3_Release(xml); if(FAILED(hres)) return display_error_page(This); hres = IStream_Seek(This->stream, off, STREAM_SEEK_SET, NULL); if(FAILED(hres)) { SysFreeString(bstr); return display_error_page(This); } hres = IStream_Write(This->stream, (BYTE*)bstr, SysStringLen(bstr)*sizeof(WCHAR), NULL); SysFreeString(bstr); if(FAILED(hres)) return display_error_page(This); return report_data(This); }
/********************************************************************** * get_nt_registry_version * * Fetch the version information from the NT-style registry keys. */ static BOOL get_nt_registry_version( RTL_OSVERSIONINFOEXW *version ) { static const WCHAR version_keyW[] = {'M','a','c','h','i','n','e','\\', 'S','o','f','t','w','a','r','e','\\', 'M','i','c','r','o','s','o','f','t','\\', 'W','i','n','d','o','w','s',' ','N','T','\\', 'C','u','r','r','e','n','t','V','e','r','s','i','o','n',0}; static const WCHAR service_pack_keyW[] = {'M','a','c','h','i','n','e','\\', 'S','y','s','t','e','m','\\', 'C','u','r','r','e','n','t','C','o','n','t','r','o','l','S','e','t','\\', 'C','o','n','t','r','o','l','\\', 'W','i','n','d','o','w','s',0}; static const WCHAR product_keyW[] = {'M','a','c','h','i','n','e','\\', 'S','y','s','t','e','m','\\', 'C','u','r','r','e','n','t','C','o','n','t','r','o','l','S','e','t','\\', 'C','o','n','t','r','o','l','\\', 'P','r','o','d','u','c','t','O','p','t','i','o','n','s',0}; static const WCHAR CurrentBuildNumberW[] = {'C','u','r','r','e','n','t','B','u','i','l','d','N','u','m','b','e','r',0}; static const WCHAR CSDVersionW[] = {'C','S','D','V','e','r','s','i','o','n',0}; static const WCHAR CurrentVersionW[] = {'C','u','r','r','e','n','t','V','e','r','s','i','o','n',0}; static const WCHAR ProductTypeW[] = {'P','r','o','d','u','c','t','T','y','p','e',0}; static const WCHAR WinNTW[] = {'W','i','n','N','T',0}; static const WCHAR ServerNTW[] = {'S','e','r','v','e','r','N','T',0}; static const WCHAR LanmanNTW[] = {'L','a','n','m','a','n','N','T',0}; OBJECT_ATTRIBUTES attr; UNICODE_STRING nameW, valueW; HANDLE hkey, hkey2; char tmp[64]; DWORD count; BOOL ret = FALSE; KEY_VALUE_PARTIAL_INFORMATION *info = (KEY_VALUE_PARTIAL_INFORMATION *)tmp; attr.Length = sizeof(attr); attr.RootDirectory = 0; attr.ObjectName = &nameW; attr.Attributes = 0; attr.SecurityDescriptor = NULL; attr.SecurityQualityOfService = NULL; RtlInitUnicodeString( &nameW, version_keyW ); if (NtOpenKey( &hkey, KEY_ALL_ACCESS, &attr )) return FALSE; memset( version, 0, sizeof(*version) ); RtlInitUnicodeString( &valueW, CurrentVersionW ); if (!NtQueryValueKey( hkey, &valueW, KeyValuePartialInformation, tmp, sizeof(tmp)-1, &count )) { WCHAR *p, *str = (WCHAR *)info->Data; str[info->DataLength / sizeof(WCHAR)] = 0; p = strchrW( str, '.' ); if (p) { *p++ = 0; version->dwMinorVersion = atoiW( p ); } version->dwMajorVersion = atoiW( str ); } if (version->dwMajorVersion) /* we got the main version, now fetch the other fields */ { ret = TRUE; version->dwPlatformId = VER_PLATFORM_WIN32_NT; /* get build number */ RtlInitUnicodeString( &valueW, CurrentBuildNumberW ); if (!NtQueryValueKey( hkey, &valueW, KeyValuePartialInformation, tmp, sizeof(tmp)-1, &count )) { WCHAR *str = (WCHAR *)info->Data; str[info->DataLength / sizeof(WCHAR)] = 0; version->dwBuildNumber = atoiW( str ); } /* get version description */ RtlInitUnicodeString( &valueW, CSDVersionW ); if (!NtQueryValueKey( hkey, &valueW, KeyValuePartialInformation, tmp, sizeof(tmp)-1, &count )) { DWORD len = min( info->DataLength, sizeof(version->szCSDVersion) - sizeof(WCHAR) ); memcpy( version->szCSDVersion, info->Data, len ); version->szCSDVersion[len / sizeof(WCHAR)] = 0; } /* get service pack version */ RtlInitUnicodeString( &nameW, service_pack_keyW ); if (!NtOpenKey( &hkey2, KEY_ALL_ACCESS, &attr )) { RtlInitUnicodeString( &valueW, CSDVersionW ); if (!NtQueryValueKey( hkey2, &valueW, KeyValuePartialInformation, tmp, sizeof(tmp), &count )) { if (info->DataLength >= sizeof(DWORD)) { DWORD dw = *(DWORD *)info->Data; version->wServicePackMajor = LOWORD(dw) >> 8; version->wServicePackMinor = LOWORD(dw) & 0xff; } }
static WCHAR *get_url_from_dde(void) { static const WCHAR szApplication[] = {'I','E','x','p','l','o','r','e',0}; static const WCHAR szTopic[] = {'W','W','W','_','O','p','e','n','U','R','L',0}; static const WCHAR szReturn[] = {'R','e','t','u','r','n',0}; HSZ hszApplication = 0; UINT_PTR timer = 0; int rc; WCHAR *ret = NULL; rc = DdeInitializeW(&ddeInst, ddeCb, CBF_SKIP_ALLNOTIFICATIONS | CBF_FAIL_ADVISES | CBF_FAIL_POKES, 0); if (rc != DMLERR_NO_ERROR) { WINE_ERR("Unable to initialize DDE, DdeInitialize returned %d\n", rc); goto done; } hszApplication = DdeCreateStringHandleW(ddeInst, szApplication, CP_WINUNICODE); if (!hszApplication) { WINE_ERR("Unable to initialize DDE, DdeCreateStringHandle failed\n"); goto done; } hszTopic = DdeCreateStringHandleW(ddeInst, szTopic, CP_WINUNICODE); if (!hszTopic) { WINE_ERR("Unable to initialize DDE, DdeCreateStringHandle failed\n"); goto done; } hszReturn = DdeCreateStringHandleW(ddeInst, szReturn, CP_WINUNICODE); if (!hszReturn) { WINE_ERR("Unable to initialize DDE, DdeCreateStringHandle failed\n"); goto done; } if (!DdeNameService(ddeInst, hszApplication, 0, DNS_REGISTER)) { WINE_ERR("Unable to initialize DDE, DdeNameService failed\n"); goto done; } timer = SetTimer(NULL, 0, 5000, NULL); if (!timer) { WINE_ERR("SetTimer failed to create timer\n"); goto done; } while (!ddeString) { MSG msg; if (!GetMessageW(&msg, NULL, 0, 0)) break; if (msg.message == WM_TIMER) break; DispatchMessageW(&msg); } if (ddeString) { if (*ddeString == '"') { WCHAR *endquote = strchrW(ddeString + 1, '"'); if (!endquote) { WINE_ERR("Unable to retrieve URL from string %s\n", wine_dbgstr_w(ddeString)); goto done; } *endquote = 0; ret = ddeString+1; } else ret = ddeString; } done: if (timer) KillTimer(NULL, timer); if (ddeInst) { if (hszTopic && hszApplication) DdeNameService(ddeInst, hszApplication, 0, DNS_UNREGISTER); if (hszReturn) DdeFreeStringHandle(ddeInst, hszReturn); if (hszTopic) DdeFreeStringHandle(ddeInst, hszTopic); if (hszApplication) DdeFreeStringHandle(ddeInst, hszApplication); DdeUninitialize(ddeInst); } return ret; }
static int reg_delete(WCHAR *key_name, WCHAR *value_name, BOOL value_empty, BOOL value_all, BOOL force) { LPWSTR p; HKEY root,subkey; static const WCHAR stubW[] = {'D','E','L','E','T','E', ' ','-',' ','%','s',' ','%','s',' ','%','d',' ','%','d',' ','%','d','\n' ,0}; reg_printfW(stubW, key_name, value_name, value_empty, value_all, force); if (!sane_path(key_name)) return 1; p = strchrW(key_name,'\\'); if (!p) { reg_message(STRING_INVALID_KEY); return 1; } p++; root = get_rootkey(key_name); if (!root) { reg_message(STRING_INVALID_KEY); return 1; } if (value_name && value_empty) { reg_message(STRING_INVALID_CMDLINE); return 1; } if (value_empty && value_all) { reg_message(STRING_INVALID_CMDLINE); return 1; } if (!force) { /* FIXME: Prompt for delete */ } /* Delete subtree only if no /v* option is given */ if (!value_name && !value_empty && !value_all) { if (RegDeleteTreeW(root,p)!=ERROR_SUCCESS) { reg_message(STRING_CANNOT_FIND); return 1; } reg_message(STRING_SUCCESS); return 0; } if(RegOpenKeyW(root,p,&subkey)!=ERROR_SUCCESS) { reg_message(STRING_CANNOT_FIND); return 1; } if (value_all) { LPWSTR szValue; DWORD maxValue; DWORD count; LONG rc; rc = RegQueryInfoKeyW(subkey, NULL, NULL, NULL, NULL, NULL, NULL, NULL, &maxValue, NULL, NULL, NULL); if (rc != ERROR_SUCCESS) { /* FIXME: failure */ RegCloseKey(subkey); return 1; } maxValue++; szValue = HeapAlloc(GetProcessHeap(),0,maxValue*sizeof(WCHAR)); while (1) { count = maxValue; rc = RegEnumValueW(subkey, 0, szValue, &count, NULL, NULL, NULL, NULL); if (rc == ERROR_SUCCESS) { rc = RegDeleteValueW(subkey, szValue); if (rc != ERROR_SUCCESS) break; } else break; } if (rc != ERROR_SUCCESS) { /* FIXME delete failed */ } } else if (value_name) { if (RegDeleteValueW(subkey,value_name) != ERROR_SUCCESS) { RegCloseKey(subkey); reg_message(STRING_CANNOT_FIND); return 1; } } else if (value_empty) { RegSetValueExW(subkey,NULL,0,REG_SZ,NULL,0); } RegCloseKey(subkey); reg_message(STRING_SUCCESS); return 0; }