void RimeWithWeaselHandler::_ReadClientInfo(UINT session_id, LPWSTR buffer) { std::string app_name; std::string client_type; // parse request text wbufferstream bs(buffer, WEASEL_IPC_BUFFER_LENGTH); std::wstring line; while (bs.good()) { std::getline(bs, line); if (!bs.good()) break; // file ends if (line == L".") break; const std::wstring kClientAppKey = L"session.client_app="; if (starts_with(line, kClientAppKey)) { std::wstring lwr = line; to_lower(lwr); app_name = wcstoutf8(lwr.substr(kClientAppKey.length()).c_str()); } const std::wstring kClientTypeKey = L"session.client_type="; if (starts_with(line, kClientTypeKey)) { client_type = wcstoutf8(line.substr(kClientTypeKey.length()).c_str()); } } // set app specific options if (!app_name.empty()) { RimeSetProperty(session_id, "client_app", app_name.c_str()); if (m_app_options.find(app_name) != m_app_options.end()) { AppOptions& options(m_app_options[app_name]); std::for_each(options.begin(), options.end(), [session_id](std::pair<const std::string, bool> &pair) { DLOG(INFO) << "set app option: " << pair.first << " = " << pair.second; RimeSetOption(session_id, pair.first.c_str(), Bool(pair.second)); }); } } // ime | tsf RimeSetProperty(session_id, "client_type", client_type.c_str()); // inline preedit bool inline_preedit = m_ui->style().inline_preedit && (client_type == "tsf"); RimeSetOption(session_id, "inline_preedit", Bool(inline_preedit)); // show soft cursor on weasel panel but not inline RimeSetOption(session_id, "soft_cursor", Bool(!inline_preedit)); }
LRESULT DictManagementDialog::OnBackup(WORD, WORD code, HWND, BOOL&) { int sel = user_dict_list_.GetCurSel(); if (sel < 0 || sel >= user_dict_list_.GetCount()) { MessageBox(L"請在左列選擇要導出的詞典名稱。", L":-(", MB_OK | MB_ICONINFORMATION); return 0; } boost::filesystem::wpath path; { char dir[MAX_PATH] = {0}; rime_get_api()->get_user_data_sync_dir(dir, _countof(dir)); WCHAR wdir[MAX_PATH] = {0}; MultiByteToWideChar(CP_ACP, 0, dir, -1, wdir, _countof(wdir)); path = wdir; } if (_waccess(path.wstring().c_str(), 0) != 0 && !boost::filesystem::create_directories(path)) { MessageBox(L"未能完成導出操作。會不會是同步文件夾無法訪問?", L":-(", MB_OK | MB_ICONERROR); return 0; } WCHAR dict_name[100] = {0}; user_dict_list_.GetText(sel, dict_name); path /= std::wstring(dict_name) + L".userdb.txt"; if (!api_->backup_user_dict(wcstoutf8(dict_name))) { MessageBox(L"不知哪裏出錯了,未能完成導出操作。", L":-(", MB_OK | MB_ICONERROR); return 0; } else if (_waccess(path.wstring().c_str(), 0) != 0) { MessageBox(L"咦,輸出的快照文件找不着了。", L":-(", MB_OK | MB_ICONERROR); return 0; } std::wstring param = L"/select, \"" + path.wstring() + L"\""; ShellExecute(NULL, L"open", L"explorer.exe", param.c_str(), NULL, SW_SHOWNORMAL); return 0; }
LRESULT DictManagementDialog::OnImport(WORD, WORD code, HWND, BOOL&) { int sel = user_dict_list_.GetCurSel(); if (sel < 0 || sel >= user_dict_list_.GetCount()) { MessageBox(L"請在左列選擇要導入的詞典名稱。", L":-(", MB_OK | MB_ICONINFORMATION); return 0; } WCHAR dict_name[MAX_PATH] = {0}; user_dict_list_.GetText(sel, dict_name); std::wstring file_name(dict_name); file_name += L"_export.txt"; CFileDialog dlg(TRUE, L"txt", file_name.c_str(), OFN_HIDEREADONLY | OFN_FILEMUSTEXIST, L"文本文檔\0*.txt\0全部文件\0*.*\0"); if (IDOK == dlg.DoModal()) { char path[MAX_PATH] = {0}; WideCharToMultiByte(CP_ACP, 0, dlg.m_szFileName, -1, path, _countof(path), NULL, NULL); int result = api_->import_user_dict(wcstoutf8(dict_name), path); if (result < 0) { MessageBox(L"不知哪裏出錯了,未能完成操作。", L":-(", MB_OK | MB_ICONERROR); } else { std::wstring report(boost::str(boost::wformat(L"導入了 %d 條記錄。") % result)); MessageBox(report.c_str(), L":-)", MB_OK | MB_ICONINFORMATION); } } return 0; }
LRESULT DictManagementDialog::OnExport(WORD, WORD code, HWND, BOOL&) { int sel = user_dict_list_.GetCurSel(); if (sel < 0 || sel >= user_dict_list_.GetCount()) { MessageBox(L"請在左列選擇要導出的詞典名稱。", L":-(", MB_OK | MB_ICONINFORMATION); return 0; } WCHAR dict_name[MAX_PATH] = {0}; user_dict_list_.GetText(sel, dict_name); std::wstring file_name(dict_name); file_name += L"_export.txt"; CFileDialog dlg(FALSE, L"txt", file_name.c_str(), OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT, L"文本文檔\0*.txt\0全部文件\0*.*\0"); if (IDOK == dlg.DoModal()) { char path[MAX_PATH] = {0}; WideCharToMultiByte(CP_ACP, 0, dlg.m_szFileName, -1, path, _countof(path), NULL, NULL); int result = api_->export_user_dict(wcstoutf8(dict_name), path); if (result < 0) { MessageBox(L"不知哪裏出錯了,未能完成操作。", L":-(", MB_OK | MB_ICONERROR); } else if (_waccess(dlg.m_szFileName, 0) != 0) { MessageBox(L"咦,導出的文件找不着了。", L":-(", MB_OK | MB_ICONERROR); } else { std::wstring report(boost::str(boost::wformat(L"導出了 %d 條記錄。") % result)); MessageBox(report.c_str(), L":-)", MB_OK | MB_ICONINFORMATION); std::wstring param = L"/select, \"" + std::wstring(dlg.m_szFileName) + L"\""; ShellExecute(NULL, L"open", L"explorer.exe", param.c_str(), NULL, SW_SHOWNORMAL); } } return 0; }
/* base::file.choose */ SEXP attribute_hidden do_filechoose(SEXP call, SEXP op, SEXP args, SEXP rho) { SEXP ans; wchar_t *fn; char str[4*MAX_PATH+1]; checkArity(op, args); setuserfilterW(L"All files (*.*)\0*.*\0\0"); fn = askfilenameW(G_("Select file"), ""); if (!fn) error(_("file choice cancelled")); wcstoutf8(str, fn, 4*MAX_PATH+1); PROTECT(ans = allocVector(STRSXP, 1)); SET_STRING_ELT(ans, 0, mkCharCE(str, CE_UTF8)); UNPROTECT(1); return ans; }
static SQLCHAR * strdup_WtoU8 (SQLWCHAR * str) { SQLCHAR *ret; size_t len; if (!str) return NULL; len = calc_len_for_utf8 (str, SQL_NTS); if ((ret = (SQLCHAR *) malloc (len + 1)) == NULL) return NULL; len = wcstoutf8 (str, ret, len); ret[len] = '\0'; return ret; }
SEXP readClipboard(SEXP sformat, SEXP sraw) { SEXP ans = R_NilValue; HGLOBAL hglb; const char *pc; int j, format, raw, size; format = asInteger(sformat); raw = asLogical(sraw); if(OpenClipboard(NULL)) { if(IsClipboardFormatAvailable(format) && (hglb = GetClipboardData(format)) && (pc = (const char *) GlobalLock(hglb))) { if(raw) { Rbyte *pans; size = GlobalSize(hglb); ans = allocVector(RAWSXP, size); /* no R allocation below */ pans = RAW(ans); for (j = 0; j < size; j++) pans[j] = *pc++; } else if (format == CF_UNICODETEXT) { int n, ienc = CE_NATIVE; const wchar_t *wpc = (wchar_t *) pc; n = wcslen(wpc); char text[2 * (n+1)]; /* UTF-8 is at most 1.5x longer */ R_CheckStack(); wcstoutf8(text, wpc, n+1); if(!strIsASCII(text)) ienc = CE_UTF8; ans = splitClipboardText(text, ienc); } else if (format == CF_TEXT || format == CF_OEMTEXT || format == CF_DIF) { /* can we get the encoding out of a CF_LOCALE entry? */ ans = splitClipboardText(pc, 0); } else error("'raw = FALSE' and format is a not a known text format"); GlobalUnlock(hglb); } CloseClipboard(); } return ans; }
static void editorsaveas(editor c) { textbox t = getdata(c); EditorData p = getdata(t); wchar_t *wname; setuserfilterW(L"R files (*.R)\0*.R\0S files (*.q, *.ssc, *.S)\0*.q;*.ssc;*.S\0All files (*.*)\0*.*\0\0"); wname = askfilesaveW(G_("Save script as"), ""); if (wname) { char name[4*MAX_PATH+1]; wcstoutf8(name, wname, MAX_PATH); /* now check if it has an extension */ char *q = strchr(name, '.'); if(!q) strncat(name, ".R", 4*MAX_PATH); editor_save_file(c, name, CE_UTF8); p->file = 1; reEnc2(name, p->filename, MAX_PATH+1, CE_UTF8, CE_NATIVE, 3); gsetmodified(t, 0); editor_set_title(c, p->filename); } show(c); }
static void editoropen(const char *default_name) { wchar_t *wname; char name[4*MAX_PATH], title[4*MAX_PATH]; int i; textbox t; EditorData p; setuserfilterW(L"R files (*.R)\0*.R\0S files (*.q, *.ssc, *.S)\0*.q;*.ssc;*.S\0All files (*.*)\0*.*\0\0"); wname = askfilenameW(G_("Open script"), default_name); /* returns NULL if open dialog cancelled */ if (wname) { wcstoutf8(name, wname, MAX_PATH); /* check if file is already open in an editor. If so, close and open again */ for (i = 0; i < neditors; ++i) { t = getdata(REditors[i]); p = getdata(t); if (!strcmp (name, p->filename)) { editorclose(REditors[i]); break; } } reEnc2(name, title, MAX_PATH+1, CE_UTF8, CE_NATIVE, 3); Rgui_Edit(name, CE_UTF8, title, 0); } else show(RConsole); }
codecvt_base::result codecvt_utf8::do_out(mbstate_t &state, const wchar_t *from, const wchar_t *from_end, const wchar_t *&from_next, char *to, char *to_limit, char *&to_next) const { result retval = codecvt_base::error; int srclen = from_end - from; int destsize = to_limit - to; int res = wcstoutf8(from, &srclen, to, &destsize); from_next = from + srclen; to_next = to + destsize; if (res < 0) { return codecvt_base::error; } else if (res == 1) { return codecvt_base::partial; } return codecvt_base::ok; }
/* utils::shortPathName */ SEXP in_shortpath(SEXP paths) { SEXP ans, el; int i, n = LENGTH(paths); char tmp[MAX_PATH]; wchar_t wtmp[32768]; DWORD res; const void *vmax = vmaxget(); if(!isString(paths)) error(_("'path' must be a character vector")); PROTECT(ans = allocVector(STRSXP, n)); for (i = 0; i < n; i++) { el = STRING_ELT(paths, i); if(getCharCE(el) == CE_UTF8) { res = GetShortPathNameW(filenameToWchar(el, FALSE), wtmp, 32768); if (res && res <= 32768) wcstoutf8(tmp, wtmp, wcslen(wtmp)+1); else strcpy(tmp, translateChar(el)); /* documented to return paths using \, which the API call does not necessarily do */ R_fixbackslash(tmp); SET_STRING_ELT(ans, i, mkCharCE(tmp, CE_UTF8)); } else { res = GetShortPathName(translateChar(el), tmp, MAX_PATH); if (res == 0 || res > MAX_PATH) strcpy(tmp, translateChar(el)); /* documented to return paths using \, which the API call does not necessarily do */ R_fixbackslash(tmp); SET_STRING_ELT(ans, i, mkChar(tmp)); } } UNPROTECT(1); vmaxset(vmax); return ans; }
/* GetNativeSystemInfo is XP or later */ pGNSI = (PGNSI) GetProcAddress(GetModuleHandle(TEXT("kernel32.dll")), "GetNativeSystemInfo"); if(NULL != pGNSI) pGNSI(&si); else GetSystemInfo(&si); if(si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_AMD64) strcat(ver, " x64"); } SET_STRING_ELT(ans, 1, mkChar(ver)); if((int)osvi.dwMajorVersion >= 5) { if(osvi.wServicePackMajor > 0) snprintf(ver, 256, "build %d, Service Pack %d", LOWORD(osvi.dwBuildNumber), (int) osvi.wServicePackMajor); else snprintf(ver, 256, "build %d", LOWORD(osvi.dwBuildNumber)); } else snprintf(ver, 256, "build %d, %s", LOWORD(osvi.dwBuildNumber), osvi.szCSDVersion); SET_STRING_ELT(ans, 2, mkChar(ver)); GetComputerNameW(name, &namelen); wcstoutf8(buf, name, 1000); SET_STRING_ELT(ans, 3, mkCharCE(buf, CE_UTF8)); #ifdef WIN64 SET_STRING_ELT(ans, 4, mkChar("x86-64")); #else SET_STRING_ELT(ans, 4, mkChar("x86")); #endif GetUserNameW(user, &userlen); wcstoutf8(buf, user, 1000); SET_STRING_ELT(ans, 5, mkCharCE(buf, CE_UTF8)); SET_STRING_ELT(ans, 6, STRING_ELT(ans, 5)); SET_STRING_ELT(ans, 7, STRING_ELT(ans, 5)); PROTECT(ansnames = allocVector(STRSXP, 8)); SET_STRING_ELT(ansnames, 0, mkChar("sysname")); SET_STRING_ELT(ansnames, 1, mkChar("release")); SET_STRING_ELT(ansnames, 2, mkChar("version")); SET_STRING_ELT(ansnames, 3, mkChar("nodename")); SET_STRING_ELT(ansnames, 4, mkChar("machine")); SET_STRING_ELT(ansnames, 5, mkChar("login")); SET_STRING_ELT(ansnames, 6, mkChar("user")); SET_STRING_ELT(ansnames, 7, mkChar("effective_user")); setAttrib(ans, R_NamesSymbol, ansnames); UNPROTECT(2); return ans; } SEXP do_syssleep(SEXP call, SEXP op, SEXP args, SEXP rho) { DWORD mtime; int ntime; double time; checkArity(op, args); time = asReal(CAR(args)); if (ISNAN(time) || time < 0) errorcall(call, _("invalid '%s' value"), "time"); ntime = 1000*(time) + 0.5; while (ntime > 0) { mtime = min(500, ntime); ntime -= mtime; Sleep(mtime); R_ProcessEvents(); } return R_NilValue; } #ifdef LEA_MALLOC #define MALLINFO_FIELD_TYPE size_t struct mallinfo { MALLINFO_FIELD_TYPE arena; /* non-mmapped space allocated from system */ MALLINFO_FIELD_TYPE ordblks; /* number of free chunks */ MALLINFO_FIELD_TYPE smblks; /* number of fastbin blocks */ MALLINFO_FIELD_TYPE hblks; /* number of mmapped regions */ MALLINFO_FIELD_TYPE hblkhd; /* space in mmapped regions */ MALLINFO_FIELD_TYPE usmblks; /* maximum total allocated space */ MALLINFO_FIELD_TYPE fsmblks; /* space available in freed fastbin blocks */ MALLINFO_FIELD_TYPE uordblks; /* total allocated space */ MALLINFO_FIELD_TYPE fordblks; /* total free space */ MALLINFO_FIELD_TYPE keepcost; /* top-most, releasable (via malloc_trim) space */ }; extern R_size_t R_max_memory; struct mallinfo mallinfo(void); #endif SEXP in_memsize(SEXP ssize) { SEXP ans; int maxmem = NA_LOGICAL; if(isLogical(ssize)) maxmem = asLogical(ssize); else if(isReal(ssize)) { R_size_t newmax; double mem = asReal(ssize); if (!R_FINITE(mem)) error(_("incorrect argument")); #ifdef LEA_MALLOC #ifndef WIN64 if(mem >= 4096) error(_("don't be silly!: your machine has a 4Gb address limit")); #endif newmax = mem * 1048576.0; if (newmax < R_max_memory) warning(_("cannot decrease memory limit: ignored")); else R_max_memory = newmax; #endif } else error(_("incorrect argument")); PROTECT(ans = allocVector(REALSXP, 1)); #ifdef LEA_MALLOC if(maxmem == NA_LOGICAL) REAL(ans)[0] = R_max_memory; else if(maxmem) REAL(ans)[0] = mallinfo().usmblks; else REAL(ans)[0] = mallinfo().uordblks; REAL(ans)[0] /= 1048576.0; #else REAL(ans)[0] = NA_REAL; #endif UNPROTECT(1); return ans; } SEXP do_dllversion(SEXP call, SEXP op, SEXP args, SEXP rho) { SEXP path = R_NilValue, ans; const wchar_t *dll; DWORD dwVerInfoSize; DWORD dwVerHnd; checkArity(op, args); path = CAR(args); if(!isString(path) || LENGTH(path) != 1) errorcall(call, _("invalid '%s' argument"), "path"); dll = filenameToWchar(STRING_ELT(path, 0), FALSE); dwVerInfoSize = GetFileVersionInfoSizeW(dll, &dwVerHnd); PROTECT(ans = allocVector(STRSXP, 2)); SET_STRING_ELT(ans, 0, mkChar("")); SET_STRING_ELT(ans, 1, mkChar("")); if (dwVerInfoSize) { BOOL fRet; LPSTR lpstrVffInfo; LPSTR lszVer = NULL; UINT cchVer = 0; lpstrVffInfo = (LPSTR) malloc(dwVerInfoSize); if (GetFileVersionInfoW(dll, 0L, dwVerInfoSize, lpstrVffInfo)) { fRet = VerQueryValue(lpstrVffInfo, TEXT("\\StringFileInfo\\040904E4\\FileVersion"), (LPVOID)&lszVer, &cchVer); if(fRet) SET_STRING_ELT(ans, 0, mkChar(lszVer)); fRet = VerQueryValue(lpstrVffInfo, TEXT("\\StringFileInfo\\040904E4\\R Version"), (LPVOID)&lszVer, &cchVer); if(fRet) SET_STRING_ELT(ans, 1, mkChar(lszVer)); else { fRet = VerQueryValue(lpstrVffInfo, TEXT("\\StringFileInfo\\040904E4\\Compiled under R Version"), (LPVOID)&lszVer, &cchVer); if(fRet) SET_STRING_ELT(ans, 1, mkChar(lszVer)); } } else ans = R_NilValue; free(lpstrVffInfo); } else ans = R_NilValue; UNPROTECT(1); return ans; } int Rwin_rename(const char *from, const char *to) { return (MoveFileEx(from, to, MOVEFILE_REPLACE_EXISTING | MOVEFILE_COPY_ALLOWED | MOVEFILE_WRITE_THROUGH) == 0); } int Rwin_wrename(const wchar_t *from, const wchar_t *to) { return (MoveFileExW(from, to, MOVEFILE_REPLACE_EXISTING | MOVEFILE_COPY_ALLOWED | MOVEFILE_WRITE_THROUGH) == 0); } const char *formatError(DWORD res) { static char buf[1000], *p; FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, NULL, res, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), buf, 1000, NULL); p = buf+strlen(buf) -1; if(*p == '\n') *p = '\0'; p = buf+strlen(buf) -1; if(*p == '\r') *p = '\0'; p = buf+strlen(buf) -1; if(*p == '.') *p = '\0'; return buf; } void R_UTF8fixslash(char *s); /* from main/util.c */ SEXP do_normalizepath(SEXP call, SEXP op, SEXP args, SEXP rho) { SEXP ans, paths = CAR(args), el, slash; int i, n = LENGTH(paths), res; char tmp[MAX_PATH], longpath[MAX_PATH], *tmp2; wchar_t wtmp[32768], wlongpath[32768], *wtmp2; int mustWork, fslash = 0; checkArity(op, args); if(!isString(paths)) errorcall(call, _("'path' must be a character vector")); slash = CADR(args); if(!isString(slash) || LENGTH(slash) != 1) errorcall(call, "'winslash' must be a character string"); const char *sl = CHAR(STRING_ELT(slash, 0)); if (strcmp(sl, "/") && strcmp(sl, "\\")) errorcall(call, "'winslash' must be '/' or '\\\\'"); if (strcmp(sl, "/") == 0) fslash = 1; mustWork = asLogical(CADDR(args)); PROTECT(ans = allocVector(STRSXP, n)); for (i = 0; i < n; i++) { int warn = 0; SEXP result; el = STRING_ELT(paths, i); result = el; if(getCharCE(el) == CE_UTF8) { if ((res = GetFullPathNameW(filenameToWchar(el, FALSE), 32768, wtmp, &wtmp2)) && res <= 32768) { if ((res = GetLongPathNameW(wtmp, wlongpath, 32768)) && res <= 32768) { wcstoutf8(longpath, wlongpath, wcslen(wlongpath)+1); if(fslash) R_UTF8fixslash(longpath); result = mkCharCE(longpath, CE_UTF8); } else if(mustWork == 1) { errorcall(call, "path[%d]=\"%s\": %s", i+1, translateChar(el), formatError(GetLastError())); } else { wcstoutf8(tmp, wtmp, wcslen(wtmp)+1); if(fslash) R_UTF8fixslash(tmp); result = mkCharCE(tmp, CE_UTF8); warn = 1; } } else if(mustWork == 1) { errorcall(call, "path[%d]=\"%s\": %s", i+1, translateChar(el), formatError(GetLastError())); } else { if (fslash) { strcpy(tmp, translateCharUTF8(el)); R_UTF8fixslash(tmp); result = mkCharCE(tmp, CE_UTF8); } warn = 1; } if (warn && (mustWork == NA_LOGICAL)) warningcall(call, "path[%d]=\"%ls\": %s", i+1, filenameToWchar(el,FALSE), formatError(GetLastError())); } else { if ((res = GetFullPathName(translateChar(el), MAX_PATH, tmp, &tmp2)) && res <= MAX_PATH) { if ((res = GetLongPathName(tmp, longpath, MAX_PATH)) && res <= MAX_PATH) { if(fslash) R_fixslash(longpath); result = mkChar(longpath); } else if(mustWork == 1) { errorcall(call, "path[%d]=\"%s\": %s", i+1, translateChar(el), formatError(GetLastError())); } else { if(fslash) R_fixslash(tmp); result = mkChar(tmp); warn = 1; } } else if(mustWork == 1) { errorcall(call, "path[%d]=\"%s\": %s", i+1, translateChar(el), formatError(GetLastError())); } else { if (fslash) { strcpy(tmp, translateChar(el)); R_fixslash(tmp); result = mkChar(tmp); } warn = 1; } if (warn && (mustWork == NA_LOGICAL)) warningcall(call, "path[%d]=\"%s\": %s", i+1, translateChar(el), formatError(GetLastError())); } SET_STRING_ELT(ans, i, result); } UNPROTECT(1); return ans; }
/* base::Sys.info */ SEXP do_sysinfo(SEXP call, SEXP op, SEXP args, SEXP rho) { SEXP ans, ansnames; OSVERSIONINFOEX osvi; char ver[256], buf[1000]; wchar_t name[MAX_COMPUTERNAME_LENGTH + 1], user[UNLEN+1]; DWORD namelen = MAX_COMPUTERNAME_LENGTH + 1, userlen = UNLEN+1; checkArity(op, args); PROTECT(ans = allocVector(STRSXP, 8)); osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFOEX); if(!GetVersionEx((OSVERSIONINFO *)&osvi)) error(_("unsupported version of Windows")); SET_STRING_ELT(ans, 0, mkChar("Windows")); /* Here for unknown future versions */ snprintf(ver, 256, "%d.%d", (int)osvi.dwMajorVersion, (int)osvi.dwMinorVersion); if((int)osvi.dwMajorVersion >= 5) { PGNSI pGNSI; SYSTEM_INFO si; if(osvi.dwMajorVersion == 6) { if(osvi.wProductType == VER_NT_WORKSTATION) { if(osvi.dwMinorVersion == 0) strcpy(ver, "Vista"); else strcpy(ver, "7"); } else strcpy(ver, "Server 2008"); } if(osvi.dwMajorVersion == 5 && osvi.dwMinorVersion == 0) strcpy(ver, "2000"); if(osvi.dwMajorVersion == 5 && osvi.dwMinorVersion == 1) strcpy(ver, "XP"); if(osvi.dwMajorVersion == 5 && osvi.dwMinorVersion == 2) { if(osvi.wProductType == VER_NT_WORKSTATION) strcpy(ver, "XP Professional"); else strcpy(ver, "Server 2003"); } /* GetNativeSystemInfo is XP or later */ pGNSI = (PGNSI) GetProcAddress(GetModuleHandle(TEXT("kernel32.dll")), "GetNativeSystemInfo"); if(NULL != pGNSI) pGNSI(&si); else GetSystemInfo(&si); if(si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_AMD64) strcat(ver, " x64"); } SET_STRING_ELT(ans, 1, mkChar(ver)); if((int)osvi.dwMajorVersion >= 5) { if(osvi.wServicePackMajor > 0) snprintf(ver, 256, "build %d, Service Pack %d", LOWORD(osvi.dwBuildNumber), (int) osvi.wServicePackMajor); else snprintf(ver, 256, "build %d", LOWORD(osvi.dwBuildNumber)); } else snprintf(ver, 256, "build %d, %s", LOWORD(osvi.dwBuildNumber), osvi.szCSDVersion); SET_STRING_ELT(ans, 2, mkChar(ver)); GetComputerNameW(name, &namelen); wcstoutf8(buf, name, 1000); SET_STRING_ELT(ans, 3, mkCharCE(buf, CE_UTF8)); #ifdef WIN64 SET_STRING_ELT(ans, 4, mkChar("x86-64")); #else SET_STRING_ELT(ans, 4, mkChar("x86")); #endif GetUserNameW(user, &userlen); wcstoutf8(buf, user, 1000); SET_STRING_ELT(ans, 5, mkCharCE(buf, CE_UTF8)); SET_STRING_ELT(ans, 6, STRING_ELT(ans, 5)); SET_STRING_ELT(ans, 7, STRING_ELT(ans, 5)); PROTECT(ansnames = allocVector(STRSXP, 8)); SET_STRING_ELT(ansnames, 0, mkChar("sysname")); SET_STRING_ELT(ansnames, 1, mkChar("release")); SET_STRING_ELT(ansnames, 2, mkChar("version")); SET_STRING_ELT(ansnames, 3, mkChar("nodename")); SET_STRING_ELT(ansnames, 4, mkChar("machine")); SET_STRING_ELT(ansnames, 5, mkChar("login")); SET_STRING_ELT(ansnames, 6, mkChar("user")); SET_STRING_ELT(ansnames, 7, mkChar("effective_user")); setAttrib(ans, R_NamesSymbol, ansnames); UNPROTECT(2); return ans; }
SEXP attribute_hidden do_getenv(SEXP call, SEXP op, SEXP args, SEXP env) { int i, j; SEXP ans; checkArity(op, args); if (!isString(CAR(args))) error(_("wrong type for argument")); if (!isString(CADR(args)) || LENGTH(CADR(args)) != 1) error(_("wrong type for argument")); i = LENGTH(CAR(args)); if (i == 0) { #ifdef Win32 int n = 0, N; wchar_t **w; for (i = 0, w = _wenviron; *w != NULL; i++, w++) n = max(n, wcslen(*w)); N = 3*n+1; char buf[N]; PROTECT(ans = allocVector(STRSXP, i)); for (i = 0, w = _wenviron; *w != NULL; i++, w++) { wcstoutf8(buf, *w, N); buf[N-1] = '\0'; SET_STRING_ELT(ans, i, mkCharCE(buf, CE_UTF8)); } #else char **e; for (i = 0, e = environ; *e != NULL; i++, e++); PROTECT(ans = allocVector(STRSXP, i)); for (i = 0, e = environ; *e != NULL; i++, e++) SET_STRING_ELT(ans, i, mkChar(*e)); #endif } else { PROTECT(ans = allocVector(STRSXP, i)); for (j = 0; j < i; j++) { #ifdef Win32 const wchar_t *wnm = wtransChar(STRING_ELT(CAR(args), j)); wchar_t *w = _wgetenv(wnm); if (w == NULL) SET_STRING_ELT(ans, j, STRING_ELT(CADR(args), 0)); else { int n = wcslen(w), N = 3*n+1; /* UCS-2 maps to <=3 UTF-8 */ R_CheckStack2(N); char buf[N]; wcstoutf8(buf, w, N); buf[N-1] = '\0'; /* safety */ SET_STRING_ELT(ans, j, mkCharCE(buf, CE_UTF8)); } #else char *s = getenv(translateChar(STRING_ELT(CAR(args), j))); if (s == NULL) SET_STRING_ELT(ans, j, STRING_ELT(CADR(args), 0)); else { SEXP tmp; if(known_to_be_latin1) tmp = mkCharCE(s, CE_LATIN1); else if(known_to_be_utf8) tmp = mkCharCE(s, CE_UTF8); else tmp = mkChar(s); SET_STRING_ELT(ans, j, tmp); } #endif } } UNPROTECT(1); return (ans); }
static SEXP mkCharUTF8(const wchar_t *wc) { char s[4*MAX_PATH]; wcstoutf8(s, wc, 4*MAX_PATH); return mkCharCE(s, CE_UTF8); }
bool RimeWithWeaselHandler::_Respond(UINT session_id, EatLine eat) { std::set<std::string> actions; std::list<std::string> messages; // extract information RIME_STRUCT(RimeCommit, commit); if (RimeGetCommit(session_id, &commit)) { actions.insert("commit"); messages.push_back(std::string("commit=") + commit.text + '\n'); RimeFreeCommit(&commit); } bool is_composing = false; RIME_STRUCT(RimeStatus, status); if (RimeGetStatus(session_id, &status)) { is_composing = !!status.is_composing; actions.insert("status"); messages.push_back(std::string("status.ascii_mode=") + std::to_string(status.is_ascii_mode) + '\n'); messages.push_back(std::string("status.composing=") + std::to_string(status.is_composing) + '\n'); messages.push_back(std::string("status.disabled=") + std::to_string(status.is_disabled) + '\n'); RimeFreeStatus(&status); } RIME_STRUCT(RimeContext, ctx); if (RimeGetContext(session_id, &ctx)) { if (is_composing) { actions.insert("ctx"); switch (m_ui->style().preedit_type) { case weasel::UIStyle::PREVIEW: if (ctx.commit_text_preview != NULL) { std::string first = ctx.commit_text_preview; messages.push_back(std::string("ctx.preedit=") + first + '\n'); messages.push_back(std::string("ctx.preedit.cursor=") + std::to_string(utf8towcslen(first.c_str(), 0)) + ',' + std::to_string(utf8towcslen(first.c_str(), first.size())) + '\n'); break; } // no preview, fall back to composition case weasel::UIStyle::COMPOSITION: messages.push_back(std::string("ctx.preedit=") + ctx.composition.preedit + '\n'); if (ctx.composition.sel_start <= ctx.composition.sel_end) { messages.push_back(std::string("ctx.preedit.cursor=") + std::to_string(utf8towcslen(ctx.composition.preedit, ctx.composition.sel_start)) + ',' + std::to_string(utf8towcslen(ctx.composition.preedit, ctx.composition.sel_end)) + '\n'); } break; } } if (ctx.menu.num_candidates) { weasel::CandidateInfo cinfo; std::wstringstream ss; boost::archive::text_woarchive oa(ss); _GetCandidateInfo(cinfo, ctx); oa << cinfo; messages.push_back(std::string("ctx.cand=") + wcstoutf8(ss.str().c_str()) + '\n'); } RimeFreeContext(&ctx); } // configuration information actions.insert("config"); messages.push_back(std::string("config.inline_preedit=") + std::to_string((int)m_ui->style().inline_preedit) + '\n'); // style bool has_synced = RimeGetOption(session_id, "__synced"); if (!has_synced) { std::wstringstream ss; boost::archive::text_woarchive oa(ss); oa << m_ui->style(); actions.insert("style"); messages.push_back(std::string("style=") + wcstoutf8(ss.str().c_str()) + '\n'); RimeSetOption(session_id, "__synced", true); } // summarize if (actions.empty()) { messages.insert(messages.begin(), std::string("action=noop\n")); } else { std::string actionList(join(actions, ",")); messages.insert(messages.begin(), std::string("action=") + actionList + '\n'); } messages.push_back(std::string(".\n")); return std::all_of(messages.begin(), messages.end(), [&eat](std::string &msg) { return eat(std::wstring(utf8towcs(msg.c_str()))); }); }