#include "InstallerMain.h" #include "InstallerUtil.h" #include "PerformInstall.h" struct folder_t { TCHAR path[MAX_PATH]; }; ICopyMethod *g_pCopyMethod = NULL; bool do_not_copy_binaries = false; TCHAR source_path[MAX_PATH]; void SetInstallMethod(ICopyMethod *pCopyMethod) { g_pCopyMethod = pCopyMethod; } bool CopyStructureRecursively(const TCHAR *basepath, const TCHAR *local_path, TCHAR *errbuf, size_t maxchars) { HANDLE hFind; WIN32_FIND_DATA fd; TCHAR search_path[MAX_PATH]; folder_t *folder_list = NULL; unsigned int folder_count = 0; if (local_path == NULL) { UTIL_PathFormat(search_path, sizeof(search_path) / sizeof(TCHAR), _T("%s\\*.*"), basepath); } else { UTIL_PathFormat(search_path, sizeof(search_path) / sizeof(TCHAR), _T("%s\\%s\\*.*"), basepath, local_path); } if (!g_pCopyMethod->SetCurrentFolder(local_path, errbuf, maxchars)) { /* :TODO: set fail state */ return false; } if ((hFind = FindFirstFile(search_path, &fd)) == INVALID_HANDLE_VALUE) { /* :TODO: set a fail state */ return false; } do { if (tstrcasecmp(fd.cFileName, _T(".")) == 0 || tstrcasecmp(fd.cFileName, _T("..")) == 0) { continue; } if ((fd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) == FILE_ATTRIBUTE_DIRECTORY) { /* We cache the folder list so we don't have to keep changing folders back and forth, * which could be annoying on a slow copy connection. */ if (folder_list == NULL) { folder_list = (folder_t *)malloc(sizeof(folder_t) * (folder_count + 1)); } else { folder_list = (folder_t *)realloc(folder_list, sizeof(folder_t) * (folder_count + 1)); } UTIL_Format(folder_list[folder_count].path, MAX_PATH, _T("%s"), fd.cFileName); folder_count++; } else { TCHAR file_path[MAX_PATH]; if (local_path == NULL) { UTIL_PathFormat(file_path, sizeof(file_path), _T("%s\\%s"), basepath, fd.cFileName); } else { UTIL_PathFormat(file_path, sizeof(file_path), _T("%s\\%s\\%s"), basepath, local_path, fd.cFileName); } if (!g_pCopyMethod->SendFile(file_path, errbuf, maxchars)) { FindClose(hFind); free(folder_list); return false; } } } while (FindNextFile(hFind, &fd)); FindClose(hFind); /* Now copy folders */ for (unsigned int i = 0; i < folder_count; i++) { /* Try creating the folder */ if (!g_pCopyMethod->CreateFolder(folder_list[i].path, errbuf, maxchars)) { free(folder_list); return false; } TCHAR new_local_path[MAX_PATH]; if (local_path == NULL) { UTIL_PathFormat(new_local_path, sizeof(new_local_path) / sizeof(TCHAR), _T("%s"), folder_list[i].path); } else { UTIL_PathFormat(new_local_path, sizeof(new_local_path) / sizeof(TCHAR), _T("%s\\%s"), local_path, folder_list[i].path); } if (!CopyStructureRecursively(basepath, new_local_path, errbuf, maxchars)) { free(folder_list); return false; } } free(folder_list); return true; } bool StartInstallProcess(HWND hWnd) { if (g_pCopyMethod->CheckForExistingInstall()) { int val = MessageBox( hWnd, _T("It looks like a previous SourceMod installation exists. Do you want to upgrade? Select \"Yes\" to upgrade and keep configuration files. Select \"No\" to perform a full re-install."), _T("SourceMod Installer"), MB_YESNO|MB_ICONQUESTION); if (val == 0 || val == IDYES) { do_not_copy_binaries = true; } else { do_not_copy_binaries = false; } } TCHAR cur_path[MAX_PATH]; if (_tgetcwd(cur_path, sizeof(cur_path)) == NULL) { MessageBox( hWnd, _T("Could not locate current directory!"), _T("SourceMod Installer"), MB_OK|MB_ICONERROR); return false; } UTIL_PathFormat(source_path, sizeof(source_path) / sizeof(TCHAR), _T("%s\\files"), cur_path); if (GetFileAttributes(source_path) == INVALID_FILE_ATTRIBUTES) { MessageBox( hWnd, _T("Could not locate the source installation files!"), _T("SourceMod Installer"), MB_OK|MB_ICONERROR); return false; } return true; } INT_PTR CALLBACK PerformInstallHandler(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam) { switch (message) { case WM_INITDIALOG: { return (INT_PTR)TRUE; } case WM_COMMAND: { if (LOWORD(wParam) == ID_INSTALL_CANCEL || LOWORD(wParam) == ID_CLOSE) { /* :TODO: enhance */ EndDialog(hDlg, NULL); return (INT_PTR)TRUE; } break; } } return (INT_PTR)FALSE; } void *DisplayPerformInstall(HWND hWnd) { INT_PTR val; if ((val = DialogBox( g_hInstance, MAKEINTRESOURCE(IDD_PERFORM_INSTALL), hWnd, PerformInstallHandler)) == -1) { return NULL; } return (void *)val; }