/* Has same return codes as make_backup(). */ static inline int link_or_rename(const char *from, const char *to, BOOL prefer_rename, STRUCT_STAT *stp) { #ifdef SUPPORT_HARD_LINKS if (!prefer_rename) { #ifndef CAN_HARDLINK_SYMLINK if (S_ISLNK(stp->st_mode)) return 0; /* Use copy code. */ #endif #ifndef CAN_HARDLINK_SPECIAL if (IS_SPECIAL(stp->st_mode) || IS_DEVICE(stp->st_mode)) return 0; /* Use copy code. */ #endif if (do_link(from, to) == 0) { if (DEBUG_GTE(BACKUP, 1)) rprintf(FINFO, "make_backup: HLINK %s successful.\n", from); return 2; } /* We prefer to rename a regular file rather than copy it. */ if (!S_ISREG(stp->st_mode) || errno == EEXIST || errno == EISDIR) return 0; } #endif if (do_rename(from, to) == 0) { if (stp->st_nlink > 1 && !S_ISDIR(stp->st_mode)) { /* If someone has hard-linked the file into the backup * dir, rename() might return success but do nothing! */ robust_unlink(from); /* Just in case... */ } if (DEBUG_GTE(BACKUP, 1)) rprintf(FINFO, "make_backup: RENAME %s successful.\n", from); return 1; } return 0; }
char_u * transchar(int c) { int i; i = 0; if (IS_SPECIAL(c)) /* special key code, display as ~@ char */ { transchar_buf[0] = '~'; transchar_buf[1] = '@'; i = 2; c = K_SECOND(c); } if ((!chartab_initialized && ( #ifdef EBCDIC (c >= 64 && c < 255) #else (c >= ' ' && c <= '~') #endif #ifdef FEAT_FKMAP || (p_altkeymap && F_ischar(c)) #endif )) || (c < 256 && vim_isprintc_strict(c))) { /* printable character */ transchar_buf[i] = c; transchar_buf[i + 1] = NUL; } else transchar_nonprint(transchar_buf + i, c); return transchar_buf; }
/* * Try translating a <> name at (*srcp)[] to dst[]. * Return the number of characters added to dst[], zero for no match. * If there is a match, srcp is advanced to after the <> name. * dst[] must be big enough to hold the result (up to six characters)! */ int trans_special ( char_u **srcp, char_u *dst, int keycode /* prefer key code, e.g. K_DEL instead of DEL */ ) { int modifiers = 0; int key; int dlen = 0; key = find_special_key(srcp, &modifiers, keycode, FALSE); if (key == 0) return 0; /* Put the appropriate modifier in a string */ if (modifiers != 0) { dst[dlen++] = K_SPECIAL; dst[dlen++] = KS_MODIFIER; dst[dlen++] = modifiers; } if (IS_SPECIAL(key)) { dst[dlen++] = K_SPECIAL; dst[dlen++] = KEY2TERMCAP0(key); dst[dlen++] = KEY2TERMCAP1(key); } else if (has_mbyte && !keycode) dlen += (*mb_char2bytes)(key, dst + dlen); else if (keycode) dlen = (int)(add_char2buf(key, dst + dlen) - dst); else dst[dlen++] = key; return dlen; }
static int trans_special(char **bp) { if (*bp[0] != '<') return **bp; char *end = strstr(*bp, ">"); if (!end) return **bp; (*bp)++; *end = '\0'; int newkey = get_special_key_code(*bp); int keycode = *(*bp+2); if (newkey) keycode = newkey; else if (strcasecmp(HC_S_TAB, *bp) == 0) keycode = K_S_TAB; int mask = 0x0; mask |= name_to_mod_mask(*bp[0]); if (!IS_SPECIAL(keycode)) keycode = extract_modifiers(keycode, &mask); *end = '>'; *bp = (end); return keycode; }
/// Get a digraph. Used after typing CTRL-K on the command line or in normal /// mode. /// /// @param cmdline TRUE when called from the cmdline /// /// @returns composed character, or NUL when ESC was used. int get_digraph(int cmdline) { int cc; no_mapping++; int c = plain_vgetc(); no_mapping--; if (c != ESC) { // ESC cancels CTRL-K if (IS_SPECIAL(c)) { // insert special key code return c; } if (cmdline) { if ((char2cells(c) == 1) && (cmdline_star == 0)) { putcmdline(c, TRUE); } } else { add_to_showcmd(c); } no_mapping++; cc = plain_vgetc(); no_mapping--; if (cc != ESC) { // ESC cancels CTRL-K return getdigraph(c, cc, TRUE); } } return NUL; }
static int xsltFormatNumberPreSuffix(xsltDecimalFormatPtr self, xmlChar **format, xsltFormatNumberInfoPtr info) { int count=0; /* will hold total length of prefix/suffix */ while (1) { /* prefix / suffix ends at end of string or at first 'special' character */ if (**format == 0) return count; /* if next character 'escaped' just count it */ if (**format == SYMBOL_QUOTE) { if (*++(*format) == 0) return -1; if (*++(*format) != SYMBOL_QUOTE) return -1; } else if (IS_SPECIAL(self, **format)) return count; /* else treat percent/per-mille as special cases, depending on whether +ve or -ve */ else if (!info->is_negative_pattern) { /* for +ve prefix/suffix, allow only a single occurence of either */ if (**format == self->percent[0]) { if (info->is_multiplier_set) return -1; info->multiplier = 100; info->is_multiplier_set = TRUE; } else if (**format == self->permille[0]) { if (info->is_multiplier_set) return -1; info->multiplier = 1000; info->is_multiplier_set = TRUE; } } else { /* for -ve prefix/suffix, allow only single occurence & insist it's previously defined */ if (**format == self->percent[0]) { if (info->is_multiplier_set) return -1; if (info->multiplier != 100) return -1; info->is_multiplier_set = TRUE; } else if (**format == self->permille[0]) { if (info->is_multiplier_set) return -1; if (info->multiplier != 1000) return -1; info->is_multiplier_set = TRUE; } } count++; (*format)++; } }
uint16 get_del_for_flag(uint16 mode) { if (S_ISREG(mode)) return DEL_FOR_FILE; if (S_ISDIR(mode)) return DEL_FOR_DIR; if (S_ISLNK(mode)) return DEL_FOR_SYMLINK; if (IS_DEVICE(mode)) return DEL_FOR_DEVICE; if (IS_SPECIAL(mode)) return DEL_FOR_SPECIAL; exit_cleanup(RERR_UNSUPPORTED); /* IMPOSSIBLE */ }
static int xsltFormatNumberPreSuffix(xsltDecimalFormatPtr self, xmlChar **format, xsltFormatNumberInfoPtr info) { int count=0; /* will hold total length of prefix/suffix */ int len; while (1) { /* * prefix / suffix ends at end of string or at * first 'special' character */ if (**format == 0) return count; /* if next character 'escaped' just count it */ if (**format == SYMBOL_QUOTE) { if (*++(*format) == 0) return -1; } else if (IS_SPECIAL(self, *format)) return count; /* * else treat percent/per-mille as special cases, * depending on whether +ve or -ve */ else { /* * for +ve prefix/suffix, allow only a * single occurence of either */ if (xsltUTF8Charcmp(*format, self->percent) == 0) { if (info->is_multiplier_set) return -1; info->multiplier = 100; info->is_multiplier_set = TRUE; } else if (xsltUTF8Charcmp(*format, self->permille) == 0) { if (info->is_multiplier_set) return -1; info->multiplier = 1000; info->is_multiplier_set = TRUE; } } if ((len=xmlUTF8Strsize(*format, 1)) < 1) return -1; count += len; *format += len; } }
static int stat_xattr(const char *fname, STRUCT_STAT *fst) { int mode, rdev_major, rdev_minor, uid, gid, len; char buf[256]; if (am_root >= 0 || IS_DEVICE(fst->st_mode) || IS_SPECIAL(fst->st_mode)) return -1; len = sys_lgetxattr(fname, XSTAT_ATTR, buf, sizeof buf - 1); if (len >= (int)sizeof buf) { len = -1; errno = ERANGE; } if (len < 0) { if (errno == ENOTSUP || errno == ENOATTR) return -1; if (errno == EPERM && S_ISLNK(fst->st_mode)) { fst->st_uid = 0; fst->st_gid = 0; return 0; } fprintf(stderr, "failed to read xattr %s for %s: %s\n", XSTAT_ATTR, fname, strerror(errno)); return -1; } buf[len] = '\0'; if (sscanf(buf, "%o %d,%d %d:%d", &mode, &rdev_major, &rdev_minor, &uid, &gid) != 5) { fprintf(stderr, "Corrupt %s xattr attached to %s: \"%s\"\n", XSTAT_ATTR, fname, buf); exit(1); } #if _S_IFLNK != 0120000 if ((mode & (_S_IFMT)) == 0120000) mode = (mode & ~(_S_IFMT)) | _S_IFLNK; #endif fst->st_mode = mode; fst->st_rdev = MAKEDEV(rdev_major, rdev_minor); fst->st_uid = uid; fst->st_gid = gid; return 0; }
/// Translates a character /// /// @param c /// /// @return translated character. char_u* transchar(int c) { int i = 0; if (IS_SPECIAL(c)) { // special key code, display as ~@ char transchar_buf[0] = '~'; transchar_buf[1] = '@'; i = 2; c = K_SECOND(c); } if ((!chartab_initialized && (((c >= ' ') && (c <= '~')) || F_ischar(c))) || ((c < 256) && vim_isprintc_strict(c))) { // printable character transchar_buf[i] = c; transchar_buf[i + 1] = NUL; } else { transchar_nonprint(transchar_buf + i, c); } return transchar_buf; }
static void ex_getchar(Keyarg *ca) { if (IS_SPECIAL(ca->key)) return; ex.state &= ~(EX_FRESH); char instr[7] = {0,0}; if (!ca->utf8) instr[0] = ca->key; else strcpy(instr, ca->utf8); int len = strlen(instr); if (strlen(ex.line) + len >= ex.maxpos) ex.line = realloc(ex.line, ex.maxpos = (2*ex.maxpos)+len); str_ins(ex.line, instr, ex.curofs, 0); ex.curpos += cell_len(instr); ex.curofs += len; }
/* * Try translating a <> name at (*srcp)[] to dst[]. * Return the number of characters added to dst[], zero for no match. * If there is a match, srcp is advanced to after the <> name. * dst[] must be big enough to hold the result (up to six characters)! */ unsigned int trans_special ( char_u **srcp, char_u *dst, int keycode /* prefer key code, e.g. K_DEL instead of DEL */ ) { int modifiers = 0; int key; unsigned int dlen = 0; key = find_special_key(srcp, &modifiers, keycode, FALSE); if (key == 0) return 0; /* Put the appropriate modifier in a string */ if (modifiers != 0) { dst[dlen++] = K_SPECIAL; dst[dlen++] = KS_MODIFIER; dst[dlen++] = (char_u)modifiers; } if (IS_SPECIAL(key)) { dst[dlen++] = K_SPECIAL; dst[dlen++] = (char_u)KEY2TERMCAP0(key); dst[dlen++] = KEY2TERMCAP1(key); } else if (has_mbyte && !keycode) dlen += (unsigned int)(*mb_char2bytes)(key, dst + dlen); else if (keycode) { char_u *after = add_char2buf(key, dst + dlen); assert(after >= dst && (uintmax_t)(after - dst) <= UINT_MAX); dlen = (unsigned int)(after - dst); } else dst[dlen++] = (char_u)key; return dlen; }
unsigned int trans_special(const char_u **srcp, const size_t src_len, char_u *const dst, const bool keycode, const bool in_string) { int modifiers = 0; int key; unsigned int dlen = 0; key = find_special_key(srcp, src_len, &modifiers, keycode, false, in_string); if (key == 0) { return 0; } // Put the appropriate modifier in a string. if (modifiers != 0) { dst[dlen++] = K_SPECIAL; dst[dlen++] = KS_MODIFIER; dst[dlen++] = (char_u)modifiers; } if (IS_SPECIAL(key)) { dst[dlen++] = K_SPECIAL; dst[dlen++] = (char_u)KEY2TERMCAP0(key); dst[dlen++] = KEY2TERMCAP1(key); } else if (has_mbyte && !keycode) { dlen += (unsigned int)(*mb_char2bytes)(key, dst + dlen); } else if (keycode) { char_u *after = add_char2buf(key, dst + dlen); assert(after >= dst && (uintmax_t)(after - dst) <= UINT_MAX); dlen = (unsigned int)(after - dst); } else { dst[dlen++] = (char_u)key; } return dlen; }
/* * Try translating a <> name at (*srcp)[], return the key and modifiers. * srcp is advanced to after the <> name. * returns 0 if there is no match. */ int find_special_key ( char_u **srcp, int *modp, int keycode, /* prefer key code, e.g. K_DEL instead of DEL */ int keep_x_key /* don't translate xHome to Home key */ ) { char_u *last_dash; char_u *end_of_name; char_u *src; char_u *bp; int modifiers; int bit; int key; unsigned long n; int l; src = *srcp; if (src[0] != '<') return 0; /* Find end of modifier list */ last_dash = src; for (bp = src + 1; *bp == '-' || vim_isIDc(*bp); bp++) { if (*bp == '-') { last_dash = bp; if (bp[1] != NUL) { if (has_mbyte) l = mb_ptr2len(bp + 1); else l = 1; if (bp[l + 1] == '>') bp += l; /* anything accepted, like <C-?> */ } } if (bp[0] == 't' && bp[1] == '_' && bp[2] && bp[3]) bp += 3; /* skip t_xx, xx may be '-' or '>' */ else if (STRNICMP(bp, "char-", 5) == 0) { vim_str2nr(bp + 5, NULL, &l, TRUE, TRUE, NULL, NULL); bp += l + 5; break; } } if (*bp == '>') { /* found matching '>' */ end_of_name = bp + 1; /* Which modifiers are given? */ modifiers = 0x0; for (bp = src + 1; bp < last_dash; bp++) { if (*bp != '-') { bit = name_to_mod_mask(*bp); if (bit == 0x0) break; /* Illegal modifier name */ modifiers |= bit; } } /* * Legal modifier name. */ if (bp >= last_dash) { if (STRNICMP(last_dash + 1, "char-", 5) == 0 && VIM_ISDIGIT(last_dash[6])) { /* <Char-123> or <Char-033> or <Char-0x33> */ vim_str2nr(last_dash + 6, NULL, NULL, TRUE, TRUE, NULL, &n); key = (int)n; } else { /* * Modifier with single letter, or special key name. */ if (has_mbyte) l = mb_ptr2len(last_dash + 1); else l = 1; if (modifiers != 0 && last_dash[l + 1] == '>') key = PTR2CHAR(last_dash + 1); else { key = get_special_key_code(last_dash + 1); if (!keep_x_key) key = handle_x_keys(key); } } /* * get_special_key_code() may return NUL for invalid * special key name. */ if (key != NUL) { /* * Only use a modifier when there is no special key code that * includes the modifier. */ key = simplify_key(key, &modifiers); if (!keycode) { /* don't want keycode, use single byte code */ if (key == K_BS) key = BS; else if (key == K_DEL || key == K_KDEL) key = DEL; } /* * Normal Key with modifier: Try to make a single byte code. */ if (!IS_SPECIAL(key)) key = extract_modifiers(key, &modifiers); *modp = modifiers; *srcp = end_of_name; return key; } } } return 0; }
/* * Return a string which contains the name of the given key when the given * modifiers are down. */ char_u *get_special_key_name(int c, int modifiers) { static char_u string[MAX_KEY_NAME_LEN + 1]; int i, idx; int table_idx; char_u *s; string[0] = '<'; idx = 1; /* Key that stands for a normal character. */ if (IS_SPECIAL(c) && KEY2TERMCAP0(c) == KS_KEY) c = KEY2TERMCAP1(c); /* * Translate shifted special keys into unshifted keys and set modifier. * Same for CTRL and ALT modifiers. */ if (IS_SPECIAL(c)) { for (i = 0; modifier_keys_table[i] != 0; i += MOD_KEYS_ENTRY_SIZE) if ( KEY2TERMCAP0(c) == (int)modifier_keys_table[i + 1] && (int)KEY2TERMCAP1(c) == (int)modifier_keys_table[i + 2]) { modifiers |= modifier_keys_table[i]; c = TERMCAP2KEY(modifier_keys_table[i + 3], modifier_keys_table[i + 4]); break; } } /* try to find the key in the special key table */ table_idx = find_special_key_in_table(c); /* * When not a known special key, and not a printable character, try to * extract modifiers. */ if (c > 0 && (*mb_char2len)(c) == 1 ) { if (table_idx < 0 && (!vim_isprintc(c) || (c & 0x7f) == ' ') && (c & 0x80)) { c &= 0x7f; modifiers |= MOD_MASK_ALT; /* try again, to find the un-alted key in the special key table */ table_idx = find_special_key_in_table(c); } if (table_idx < 0 && !vim_isprintc(c) && c < ' ') { c += '@'; modifiers |= MOD_MASK_CTRL; } } /* translate the modifier into a string */ for (i = 0; mod_mask_table[i].name != 'A'; i++) if ((modifiers & mod_mask_table[i].mod_mask) == mod_mask_table[i].mod_flag) { string[idx++] = mod_mask_table[i].name; string[idx++] = (char_u)'-'; } if (table_idx < 0) { /* unknown special key, may output t_xx */ if (IS_SPECIAL(c)) { string[idx++] = 't'; string[idx++] = '_'; string[idx++] = (char_u)KEY2TERMCAP0(c); string[idx++] = KEY2TERMCAP1(c); } /* Not a special key, only modifiers, output directly */ else { if (has_mbyte && (*mb_char2len)(c) > 1) idx += (*mb_char2bytes)(c, string + idx); else if (vim_isprintc(c)) string[idx++] = (char_u)c; else { s = transchar(c); while (*s) string[idx++] = *s++; } } } else { /* use name of special key */ STRCPY(string + idx, key_names_table[table_idx].name); idx = (int)STRLEN(string); } string[idx++] = '>'; string[idx] = NUL; return string; }
/** * xsltFormatNumberConversion: * @self: the decimal format * @format: the format requested * @number: the value to format * @result: the place to ouput the result * * format-number() uses the JDK 1.1 DecimalFormat class: * * http://java.sun.com/products/jdk/1.1/docs/api/java.text.DecimalFormat.html * * Structure: * * pattern := subpattern{;subpattern} * subpattern := {prefix}integer{.fraction}{suffix} * prefix := '\\u0000'..'\\uFFFD' - specialCharacters * suffix := '\\u0000'..'\\uFFFD' - specialCharacters * integer := '#'* '0'* '0' * fraction := '0'* '#'* * * Notation: * X* 0 or more instances of X * (X | Y) either X or Y. * X..Y any character from X up to Y, inclusive. * S - T characters in S, except those in T * * Special Characters: * * Symbol Meaning * 0 a digit * # a digit, zero shows as absent * . placeholder for decimal separator * , placeholder for grouping separator. * ; separates formats. * - default negative prefix. * % multiply by 100 and show as percentage * ? multiply by 1000 and show as per mille * X any other characters can be used in the prefix or suffix * ' used to quote special characters in a prefix or suffix. */ xmlXPathError xsltFormatNumberConversion(xsltDecimalFormatPtr self, xmlChar *format, double number, xmlChar **result) { xmlXPathError status = XPATH_EXPRESSION_OK; xmlBufferPtr buffer; xmlChar *the_format, *prefix = NULL, *suffix = NULL; xmlChar *nprefix, *nsuffix = NULL; xmlChar pchar; int prefix_length, suffix_length = 0, nprefix_length, nsuffix_length; double scale; int j; xsltFormatNumberInfo format_info; /* delayed_multiplier allows a 'trailing' percent or permille to be treated as suffix */ int delayed_multiplier = 0; /* flag to show no -ve format present for -ve number */ char default_sign = 0; /* flag to show error found, should use default format */ char found_error = 0; *result = NULL; switch (xmlXPathIsInf(number)) { case -1: if (self->minusSign == NULL) *result = xmlStrdup(BAD_CAST "-"); else *result = xmlStrdup(self->minusSign); /* no-break on purpose */ case 1: if ((self == NULL) || (self->infinity == NULL)) *result = xmlStrcat(*result, BAD_CAST "Infinity"); else *result = xmlStrcat(*result, self->infinity); return(status); default: if (xmlXPathIsNaN(number)) { if ((self == NULL) || (self->noNumber == NULL)) *result = xmlStrdup(BAD_CAST "NaN"); else *result = xmlStrdup(self->noNumber); return(status); } } buffer = xmlBufferCreate(); if (buffer == NULL) { return XPATH_MEMORY_ERROR; } format_info.integer_digits = 0; format_info.frac_digits = 0; format_info.frac_hash = 0; format_info.group = -1; format_info.multiplier = 1; format_info.is_multiplier_set = FALSE; format_info.is_negative_pattern = FALSE; the_format = format; /* First we process the +ve pattern to get percent / permille, as well as main format */ prefix = the_format; prefix_length = xsltFormatNumberPreSuffix(self, &the_format, &format_info); if (prefix_length < 0) { found_error = 1; goto OUTPUT_NUMBER; } /* Here we process the "number" part of the format. It gets a little messy because of */ /* the percent/per-mille - if that appears at the end, it may be part of the suffix */ /* instead of part of the number, so the variable delayed_multiplier is used to handle it */ while ((*the_format != 0) && (*the_format != self->decimalPoint[0]) && (*the_format != self->patternSeparator[0])) { if (delayed_multiplier != 0) { format_info.multiplier = delayed_multiplier; format_info.is_multiplier_set = TRUE; delayed_multiplier = 0; } if (*the_format == self->digit[0]) { if (format_info.integer_digits > 0) { found_error = 1; goto OUTPUT_NUMBER; } if (format_info.group >= 0) format_info.group++; } else if (*the_format == self->zeroDigit[0]) { format_info.integer_digits++; if (format_info.group >= 0) format_info.group++; } else if (*the_format == self->grouping[0]) { /* Reset group count */ format_info.group = 0; } else if (*the_format == self->percent[0]) { if (format_info.is_multiplier_set) { found_error = 1; goto OUTPUT_NUMBER; } delayed_multiplier = 100; } else if (*the_format == self->permille[0]) { if (format_info.is_multiplier_set) { found_error = 1; goto OUTPUT_NUMBER; } delayed_multiplier = 1000; } else break; /* while */ the_format++; } /* We have finished the integer part, now work on fraction */ if (*the_format == self->decimalPoint[0]) the_format++; /* Skip over the decimal */ while (*the_format != 0) { if (*the_format == self->zeroDigit[0]) { if (format_info.frac_hash != 0) { found_error = 1; goto OUTPUT_NUMBER; } format_info.frac_digits++; } else if (*the_format == self->digit[0]) { format_info.frac_hash++; } else if (*the_format == self->percent[0]) { if (format_info.is_multiplier_set) { found_error = 1; goto OUTPUT_NUMBER; } delayed_multiplier = 100; the_format++; continue; /* while */ } else if (*the_format == self->permille[0]) { if (format_info.is_multiplier_set) { found_error = 1; goto OUTPUT_NUMBER; } delayed_multiplier = 1000; the_format++; continue; /* while */ } else if (*the_format != self->grouping[0]) { break; /* while */ } the_format++; if (delayed_multiplier != 0) { format_info.multiplier = delayed_multiplier; delayed_multiplier = 0; format_info.is_multiplier_set = TRUE; } } /* If delayed_multiplier is set after processing the "number" part, should be in suffix */ if (delayed_multiplier != 0) { the_format--; delayed_multiplier = 0; } suffix = the_format; suffix_length = xsltFormatNumberPreSuffix(self, &the_format, &format_info); if ( (suffix_length < 0) || ((*the_format != 0) && (*the_format != self->patternSeparator[0])) ) { found_error = 1; goto OUTPUT_NUMBER; } /* We have processed the +ve prefix, number part and +ve suffix. */ /* If the number is -ve, we must substitute the -ve prefix / suffix */ if (number < 0) { the_format = (xmlChar *)xmlStrchr(format, self->patternSeparator[0]); if (the_format == NULL) { /* No -ve pattern present, so use default signing */ default_sign = 1; } else { /* Flag changes interpretation of percent/permille in -ve pattern */ the_format++; /* Skip over pattern separator */ format_info.is_negative_pattern = TRUE; format_info.is_multiplier_set = FALSE; /* First do the -ve prefix */ nprefix = the_format; nprefix_length = xsltFormatNumberPreSuffix(self, &the_format, &format_info); if (nprefix_length<0) { found_error = 1; goto OUTPUT_NUMBER; } /* Next skip over the -ve number info */ the_format += prefix_length; while (*the_format != 0) { if ( (*the_format == (self)->percent[0]) || (*the_format == (self)->permille[0]) ) { if (format_info.is_multiplier_set) { found_error = 1; goto OUTPUT_NUMBER; } format_info.is_multiplier_set = TRUE; delayed_multiplier = 1; } else if (IS_SPECIAL(self, *the_format)) delayed_multiplier = 0; else break; /* while */ the_format++; } if (delayed_multiplier != 0) { format_info.is_multiplier_set = FALSE; the_format--; } /* Finally do the -ve suffix */ if (*the_format != 0) { nsuffix = the_format; nsuffix_length = xsltFormatNumberPreSuffix(self, &the_format, &format_info); if (nsuffix_length < 0) { found_error = 1; goto OUTPUT_NUMBER; } } else nsuffix_length = 0; if (*the_format != 0) { found_error = 1; goto OUTPUT_NUMBER; } /* Here's another Java peculiarity: * if -ve prefix/suffix == +ve ones, discard & use default */ if ((nprefix_length != prefix_length) || (nsuffix_length != suffix_length) || ((nprefix_length > 0) && (xmlStrncmp(nprefix, prefix, prefix_length) !=0 )) || ((nsuffix_length > 0) && (xmlStrncmp(nsuffix, suffix, suffix_length) !=0 ))) { prefix = nprefix; prefix_length = nprefix_length; suffix = nsuffix; suffix_length = nsuffix_length; } else { default_sign = 1; } } } OUTPUT_NUMBER: if (found_error != 0) { xsltPrintErrorContext(NULL, NULL, NULL); xsltGenericError(xsltGenericErrorContext, "xsltFormatNumberConversion : error in format string, using default\n"); default_sign = (number < 0.0) ? 1 : 0; prefix_length = suffix_length = 0; format_info.integer_digits = 1; format_info.frac_digits = 1; format_info.frac_hash = 4; format_info.group = -1; format_info.multiplier = 1; } /* Ready to output our number. First see if "default sign" is required */ if (default_sign != 0) xmlBufferAdd(buffer, self->minusSign, 1); /* Put the prefix into the buffer */ for (j = 0; j < prefix_length; j++) { if ((pchar = *prefix++) == SYMBOL_QUOTE) { pchar = *prefix++; prefix++; } xmlBufferAdd(buffer, &pchar, 1); } /* Next do the integer part of the number */ number = fabs(number) * (double)format_info.multiplier; scale = pow(10.0, (double)(format_info.frac_digits + format_info.frac_hash)); number = floor((scale * number + 0.5)) / scale; if ((self->grouping != NULL) && (self->grouping[0] != 0)) xsltNumberFormatDecimal(buffer, floor(number), self->zeroDigit[0], format_info.integer_digits, format_info.group, (xmlChar) self->grouping[0]); else xsltNumberFormatDecimal(buffer, floor(number), self->zeroDigit[0], format_info.integer_digits, format_info.group, (xmlChar) ','); /* Next the fractional part, if required */ if (format_info.frac_digits + format_info.frac_hash > 0) { number -= floor(number); if ((number != 0) || (format_info.frac_digits != 0)) { xmlBufferAdd(buffer, self->decimalPoint, 1); number = floor(scale * number + 0.5); for (j = format_info.frac_hash; j > 0; j--) { if (fmod(number, 10.0) >= 1.0) break; /* for */ number /= 10.0; } xsltNumberFormatDecimal(buffer, floor(number), self->zeroDigit[0], format_info.frac_digits + j, 0, (xmlChar)0); } } /* Put the suffix into the buffer */ for (j = 0; j < suffix_length; j++) { if ((pchar = *suffix++) == SYMBOL_QUOTE) { pchar = *suffix++; suffix++; } xmlBufferAdd(buffer, &pchar, 1); } *result = xmlStrdup(xmlBufferContent(buffer)); xmlBufferFree(buffer); return status; }
/* * Helper function for validating a DN. This function will validate * a single RDN. If the RDN is valid, 0 will be returned, otherwise * non-zero will be returned. A pointer to the last character processed * will be set in the "last parameter. This will be the end of the RDN * in the valid case, and the illegal character in the invalid case. */ int rdn_validate( const char *begin, const char *end, const char **last ) { int rc = 0; /* Assume RDN is valid */ int numericform = 0; char *separator = NULL; const char *p = begin; /* Find the '=', then use the helpers for descr and numericoid */ if ((separator = PL_strnchr(p, '=', end - begin + 1)) == NULL) { rc = 1; goto exit; } /* Process an attribute type. The 'descr' * form must start with a 'leadkeychar'. */ if (IS_LEADKEYCHAR(*p)) { if ((rc = keystring_validate(p, separator - 1))) { goto exit; } /* See if the 'numericoid' form is being used */ } else if (isdigit(*p)) { numericform = 1; if ((rc = numericoid_validate(p, separator - 1))) { goto exit; } } else { rc = 1; goto exit; } /* Advance the pointer past the '=' and make sure * we're not past the end of the string. */ p = separator + 1; if (p > end) { rc = 1; goto exit; } /* The value must be a 'hexstring' if the 'numericoid' * form of 'attributeType' is used. Per RFC 4514: * * hexstring = SHARP 1*hexpair * hexpair = HEX HEX */ if (numericform) { if ((p == end) || !IS_SHARP(*p)) { rc = 1; goto exit; } p++; /* The value must be a 'string' when the 'descr' form * of 'attributeType' is used. Per RFC 4514: * * string = [ ( leadchar / pair ) [ *( stringchar / pair ) * ( trailchar / pair ) ] ] * * leadchar = LUTF1 / UTFMB * trailchar = TUTF1 / UTFMB * stringchar = SUTF1 / UTFMB * * pair = ESC (ESC / special / hexpair ) * special = escaped / SPACE / SHARP / EQUALS * escaped = DQUOTE / PLUS / COMMA / SEMI / LANGLE / RANGLE * hexpair = HEX HEX */ } else { /* Check the leadchar to see if anything illegal * is there. We need to allow a 'pair' to get * through, so we'll assume that a '\' is the * start of a 'pair' for now. */ if (IS_UTF1(*p) && !IS_ESC(*p) && !IS_LUTF1(*p)) { rc = 1; goto exit; } } /* Loop through string until we find the ',' separator, a '+' * char indicating a multi-value RDN, or we reach the end. */ while ((p <= end) && (*p != ',') && (*p != '+')) { if (numericform) { /* Process a single 'hexpair' */ if ((p == end) || !isxdigit(*p) || !isxdigit(*p + 1)) { rc = 1; goto exit; } p = p + 2; } else { /* Check for a valid 'stringchar'. We handle * multi-byte characters separately. */ if (IS_UTF1(*p)) { /* If we're at the end, check if we have * a valid 'trailchar'. */ if ((p == end) && !IS_TUTF1(*p)) { rc = 1; goto exit; /* Check for a 'pair'. */ } else if (IS_ESC(*p)) { /* We're guaranteed to still have at * least one more character, so lets * take a look at it. */ p++; if (!IS_ESC(*p) && !IS_SPECIAL(*p)) { /* The only thing valid now * is a 'hexpair'. */ if ((p == end) || !isxdigit(*p) ||!isxdigit(*p + 1)) { rc = 1; goto exit; } p++; } /* Only allow 'SUTF1' chars now. */ } else if (!IS_SUTF1(*p)) { rc = 1; goto exit; } p++; } else { /* Validate a single 'UTFMB' (multi-byte) character. */ if (utf8char_validate(p, end, &p ) != 0) { rc = 1; goto exit; } /* Advance the pointer past the multi-byte char. */ p++; } } } /* We'll end up either at the comma, a '+', or one past end. * If we are processing a multi-valued RDN, we recurse to * process the next 'attributeTypeAndValue'. */ if ((p <= end) && (*p == '+')) { /* Make sure that there is something after the '+'. */ if (p == end) { rc = 1; goto exit; } p++; /* Recurse to process the next value. We need to reset p to * ensure that last is set correctly for the original caller. */ rc = rdn_validate( p, end, last ); p = *last + 1; } exit: *last = p - 1; return rc; }
int find_special_key(const char_u **srcp, const size_t src_len, int *const modp, const bool keycode, const bool keep_x_key, const bool in_string) { const char_u *last_dash; const char_u *end_of_name; const char_u *src; const char_u *bp; const char_u *const end = *srcp + src_len - 1; int modifiers; int bit; int key; uvarnumber_T n; int l; if (src_len == 0) { return 0; } src = *srcp; if (src[0] != '<') { return 0; } // Find end of modifier list last_dash = src; for (bp = src + 1; bp <= end && (*bp == '-' || ascii_isident(*bp)); bp++) { if (*bp == '-') { last_dash = bp; if (bp + 1 <= end) { l = utfc_ptr2len_len(bp + 1, (int)(end - bp) + 1); // Anything accepted, like <C-?>. // <C-"> or <M-"> are not special in strings as " is // the string delimiter. With a backslash it works: <M-\"> if (end - bp > l && !(in_string && bp[1] == '"') && bp[2] == '>') { bp += l; } else if (end - bp > 2 && in_string && bp[1] == '\\' && bp[2] == '"' && bp[3] == '>') { bp += 2; } } } if (end - bp > 3 && bp[0] == 't' && bp[1] == '_') { bp += 3; // skip t_xx, xx may be '-' or '>' } else if (end - bp > 4 && STRNICMP(bp, "char-", 5) == 0) { vim_str2nr(bp + 5, NULL, &l, STR2NR_ALL, NULL, NULL, 0); bp += l + 5; break; } } if (bp <= end && *bp == '>') { // found matching '>' end_of_name = bp + 1; /* Which modifiers are given? */ modifiers = 0x0; for (bp = src + 1; bp < last_dash; bp++) { if (*bp != '-') { bit = name_to_mod_mask(*bp); if (bit == 0x0) { break; // Illegal modifier name } modifiers |= bit; } } // Legal modifier name. if (bp >= last_dash) { if (STRNICMP(last_dash + 1, "char-", 5) == 0 && ascii_isdigit(last_dash[6])) { // <Char-123> or <Char-033> or <Char-0x33> vim_str2nr(last_dash + 6, NULL, NULL, STR2NR_ALL, NULL, &n, 0); key = (int)n; } else { int off = 1; // Modifier with single letter, or special key name. if (in_string && last_dash[1] == '\\' && last_dash[2] == '"') { off = 2; } l = mb_ptr2len(last_dash + 1); if (modifiers != 0 && last_dash[l + 1] == '>') { key = PTR2CHAR(last_dash + off); } else { key = get_special_key_code(last_dash + off); if (!keep_x_key) { key = handle_x_keys(key); } } } // get_special_key_code() may return NUL for invalid // special key name. if (key != NUL) { // Only use a modifier when there is no special key code that // includes the modifier. key = simplify_key(key, &modifiers); if (!keycode) { // don't want keycode, use single byte code if (key == K_BS) { key = BS; } else if (key == K_DEL || key == K_KDEL) { key = DEL; } } // Normal Key with modifier: // Try to make a single byte code (except for Alt/Meta modifiers). if (!IS_SPECIAL(key)) { key = extract_modifiers(key, &modifiers); } *modp = modifiers; *srcp = end_of_name; return key; } } } return 0; }
/* If we have a --backup-dir, then we get here from make_backup(). * We will move the file to be deleted into a parallel directory tree. */ static int keep_backup(const char *fname) { STRUCT_STAT st; struct file_struct *file; char *buf; int kept = 0; int ret_code; /* return if no file to keep */ if (do_lstat(fname, &st) < 0) return 1; if (!(file = make_file(fname, NULL, NULL, 0, NO_FILTERS))) return 1; /* the file could have disappeared */ if (!(buf = get_backup_name(fname))) { unmake_file(file); return 0; } /* Check to see if this is a device file, or link */ if ((am_root && preserve_devices && IS_DEVICE(file->mode)) || (preserve_specials && IS_SPECIAL(file->mode))) { uint32 *devp = F_RDEV_P(file); dev_t rdev = MAKEDEV(DEV_MAJOR(devp), DEV_MINOR(devp)); do_unlink(buf); if (do_mknod(buf, file->mode, rdev) < 0 && (errno != ENOENT || make_bak_dir(buf) < 0 || do_mknod(buf, file->mode, rdev) < 0)) { rsyserr(FERROR, errno, "mknod %s failed", full_fname(buf)); } else if (verbose > 2) { rprintf(FINFO, "make_backup: DEVICE %s successful.\n", fname); } kept = 1; do_unlink(fname); } if (!kept && S_ISDIR(file->mode)) { /* make an empty directory */ if (do_mkdir(buf, file->mode) < 0 && (errno != ENOENT || make_bak_dir(buf) < 0 || do_mkdir(buf, file->mode) < 0)) { rsyserr(FINFO, errno, "mkdir %s failed", full_fname(buf)); } ret_code = do_rmdir(fname); if (verbose > 2) { rprintf(FINFO, "make_backup: RMDIR %s returns %i\n", full_fname(fname), ret_code); } kept = 1; } #ifdef SUPPORT_LINKS if (!kept && preserve_links && S_ISLNK(file->mode)) { const char *sl = F_SYMLINK(file); if (safe_symlinks && unsafe_symlink(sl, buf)) { if (verbose) { rprintf(FINFO, "ignoring unsafe symlink %s -> %s\n", full_fname(buf), sl); } kept = 1; } else { do_unlink(buf); if (do_symlink(sl, buf) < 0 && (errno != ENOENT || make_bak_dir(buf) < 0 || do_symlink(sl, buf) < 0)) { rsyserr(FERROR, errno, "link %s -> \"%s\"", full_fname(buf), sl); } do_unlink(fname); kept = 1; } } #endif if (!kept && !S_ISREG(file->mode)) { rprintf(FINFO, "make_bak: skipping non-regular file %s\n", fname); unmake_file(file); return 1; } /* move to keep tree if a file */ if (!kept) { if (robust_move(fname, buf) != 0) { rsyserr(FERROR, errno, "keep_backup failed: %s -> \"%s\"", full_fname(fname), buf); } else if (st.st_nlink > 1) { /* If someone has hard-linked the file into the backup * dir, rename() might return success but do nothing! */ robust_unlink(fname); /* Just in case... */ } } set_file_attrs(buf, file, NULL, 0); unmake_file(file); if (verbose > 1) { rprintf(FINFO, "backed up %s to %s\n", fname, buf); } return 1; }
/** * xsltFormatNumberConversion: * @self: the decimal format * @format: the format requested * @number: the value to format * @result: the place to ouput the result * * format-number() uses the JDK 1.1 DecimalFormat class: * * http://java.sun.com/products/jdk/1.1/docs/api/java.text.DecimalFormat.html * * Structure: * * pattern := subpattern{;subpattern} * subpattern := {prefix}integer{.fraction}{suffix} * prefix := '\\u0000'..'\\uFFFD' - specialCharacters * suffix := '\\u0000'..'\\uFFFD' - specialCharacters * integer := '#'* '0'* '0' * fraction := '0'* '#'* * * Notation: * X* 0 or more instances of X * (X | Y) either X or Y. * X..Y any character from X up to Y, inclusive. * S - T characters in S, except those in T * * Special Characters: * * Symbol Meaning * 0 a digit * # a digit, zero shows as absent * . placeholder for decimal separator * , placeholder for grouping separator. * ; separates formats. * - default negative prefix. * % multiply by 100 and show as percentage * ? multiply by 1000 and show as per mille * X any other characters can be used in the prefix or suffix * ' used to quote special characters in a prefix or suffix. * * Returns a possible XPath error */ xmlXPathError xsltFormatNumberConversion(xsltDecimalFormatPtr self, xmlChar *format, double number, xmlChar **result) { xmlXPathError status = XPATH_EXPRESSION_OK; xmlBufferPtr buffer; xmlChar *the_format, *prefix = NULL, *suffix = NULL; xmlChar *nprefix, *nsuffix = NULL; xmlChar pchar; int prefix_length, suffix_length = 0, nprefix_length, nsuffix_length; double scale; int j, len; int self_grouping_len; xsltFormatNumberInfo format_info; /* * delayed_multiplier allows a 'trailing' percent or * permille to be treated as suffix */ int delayed_multiplier = 0; /* flag to show no -ve format present for -ve number */ char default_sign = 0; /* flag to show error found, should use default format */ char found_error = 0; if (xmlStrlen(format) <= 0) { xsltTransformError(NULL, NULL, NULL, "xsltFormatNumberConversion : " "Invalid format (0-length)\n"); } *result = NULL; switch (xmlXPathIsInf(number)) { case -1: if (self->minusSign == NULL) *result = xmlStrdup(BAD_CAST "-"); else *result = xmlStrdup(self->minusSign); /* no-break on purpose */ case 1: if ((self == NULL) || (self->infinity == NULL)) *result = xmlStrcat(*result, BAD_CAST "Infinity"); else *result = xmlStrcat(*result, self->infinity); return(status); default: if (xmlXPathIsNaN(number)) { if ((self == NULL) || (self->noNumber == NULL)) *result = xmlStrdup(BAD_CAST "NaN"); else *result = xmlStrdup(self->noNumber); return(status); } } buffer = xmlBufferCreate(); if (buffer == NULL) { return XPATH_MEMORY_ERROR; } format_info.integer_hash = 0; format_info.integer_digits = 0; format_info.frac_digits = 0; format_info.frac_hash = 0; format_info.group = -1; format_info.multiplier = 1; format_info.add_decimal = FALSE; format_info.is_multiplier_set = FALSE; format_info.is_negative_pattern = FALSE; the_format = format; /* * First we process the +ve pattern to get percent / permille, * as well as main format */ prefix = the_format; prefix_length = xsltFormatNumberPreSuffix(self, &the_format, &format_info); if (prefix_length < 0) { found_error = 1; goto OUTPUT_NUMBER; } /* * Here we process the "number" part of the format. It gets * a little messy because of the percent/per-mille - if that * appears at the end, it may be part of the suffix instead * of part of the number, so the variable delayed_multiplier * is used to handle it */ self_grouping_len = xmlStrlen(self->grouping); while ((*the_format != 0) && (xsltUTF8Charcmp(the_format, self->decimalPoint) != 0) && (xsltUTF8Charcmp(the_format, self->patternSeparator) != 0)) { if (delayed_multiplier != 0) { format_info.multiplier = delayed_multiplier; format_info.is_multiplier_set = TRUE; delayed_multiplier = 0; } if (xsltUTF8Charcmp(the_format, self->digit) == 0) { if (format_info.integer_digits > 0) { found_error = 1; goto OUTPUT_NUMBER; } format_info.integer_hash++; if (format_info.group >= 0) format_info.group++; } else if (xsltUTF8Charcmp(the_format, self->zeroDigit) == 0) { format_info.integer_digits++; if (format_info.group >= 0) format_info.group++; } else if ((self_grouping_len > 0) && (!xmlStrncmp(the_format, self->grouping, self_grouping_len))) { /* Reset group count */ format_info.group = 0; the_format += self_grouping_len; continue; } else if (xsltUTF8Charcmp(the_format, self->percent) == 0) { if (format_info.is_multiplier_set) { found_error = 1; goto OUTPUT_NUMBER; } delayed_multiplier = 100; } else if (xsltUTF8Charcmp(the_format, self->permille) == 0) { if (format_info.is_multiplier_set) { found_error = 1; goto OUTPUT_NUMBER; } delayed_multiplier = 1000; } else break; /* while */ if ((len=xmlUTF8Strsize(the_format, 1)) < 1) { found_error = 1; goto OUTPUT_NUMBER; } the_format += len; } /* We have finished the integer part, now work on fraction */ if ( (*the_format != 0) && (xsltUTF8Charcmp(the_format, self->decimalPoint) == 0) ) { format_info.add_decimal = TRUE; if ((len = xmlUTF8Strsize(the_format, 1)) < 1) { found_error = 1; goto OUTPUT_NUMBER; } the_format += len; /* Skip over the decimal */ } while (*the_format != 0) { if (xsltUTF8Charcmp(the_format, self->zeroDigit) == 0) { if (format_info.frac_hash != 0) { found_error = 1; goto OUTPUT_NUMBER; } format_info.frac_digits++; } else if (xsltUTF8Charcmp(the_format, self->digit) == 0) { format_info.frac_hash++; } else if (xsltUTF8Charcmp(the_format, self->percent) == 0) { if (format_info.is_multiplier_set) { found_error = 1; goto OUTPUT_NUMBER; } delayed_multiplier = 100; if ((len = xmlUTF8Strsize(the_format, 1)) < 1) { found_error = 1; goto OUTPUT_NUMBER; } the_format += len; continue; /* while */ } else if (xsltUTF8Charcmp(the_format, self->permille) == 0) { if (format_info.is_multiplier_set) { found_error = 1; goto OUTPUT_NUMBER; } delayed_multiplier = 1000; if ((len = xmlUTF8Strsize(the_format, 1)) < 1) { found_error = 1; goto OUTPUT_NUMBER; } the_format += len; continue; /* while */ } else if (xsltUTF8Charcmp(the_format, self->grouping) != 0) { break; /* while */ } if ((len = xmlUTF8Strsize(the_format, 1)) < 1) { found_error = 1; goto OUTPUT_NUMBER; } the_format += len; if (delayed_multiplier != 0) { format_info.multiplier = delayed_multiplier; delayed_multiplier = 0; format_info.is_multiplier_set = TRUE; } } /* * If delayed_multiplier is set after processing the * "number" part, should be in suffix */ if (delayed_multiplier != 0) { the_format -= len; delayed_multiplier = 0; } suffix = the_format; suffix_length = xsltFormatNumberPreSuffix(self, &the_format, &format_info); if ( (suffix_length < 0) || ((*the_format != 0) && (xsltUTF8Charcmp(the_format, self->patternSeparator) != 0)) ) { found_error = 1; goto OUTPUT_NUMBER; } /* * We have processed the +ve prefix, number part and +ve suffix. * If the number is -ve, we must substitute the -ve prefix / suffix */ if (number < 0) { /* * Note that j is the number of UTF8 chars before the separator, * not the number of bytes! (bug 151975) */ j = xmlUTF8Strloc(format, self->patternSeparator); if (j < 0) { /* No -ve pattern present, so use default signing */ default_sign = 1; } else { /* Skip over pattern separator (accounting for UTF8) */ the_format = (xmlChar *)xmlUTF8Strpos(format, j + 1); /* * Flag changes interpretation of percent/permille * in -ve pattern */ format_info.is_negative_pattern = TRUE; format_info.is_multiplier_set = FALSE; /* First do the -ve prefix */ nprefix = the_format; nprefix_length = xsltFormatNumberPreSuffix(self, &the_format, &format_info); if (nprefix_length<0) { found_error = 1; goto OUTPUT_NUMBER; } while (*the_format != 0) { if ( (xsltUTF8Charcmp(the_format, (self)->percent) == 0) || (xsltUTF8Charcmp(the_format, (self)->permille)== 0) ) { if (format_info.is_multiplier_set) { found_error = 1; goto OUTPUT_NUMBER; } format_info.is_multiplier_set = TRUE; delayed_multiplier = 1; } else if (IS_SPECIAL(self, the_format)) delayed_multiplier = 0; else break; /* while */ if ((len = xmlUTF8Strsize(the_format, 1)) < 1) { found_error = 1; goto OUTPUT_NUMBER; } the_format += len; } if (delayed_multiplier != 0) { format_info.is_multiplier_set = FALSE; the_format -= len; } /* Finally do the -ve suffix */ if (*the_format != 0) { nsuffix = the_format; nsuffix_length = xsltFormatNumberPreSuffix(self, &the_format, &format_info); if (nsuffix_length < 0) { found_error = 1; goto OUTPUT_NUMBER; } } else nsuffix_length = 0; if (*the_format != 0) { found_error = 1; goto OUTPUT_NUMBER; } /* * Here's another Java peculiarity: * if -ve prefix/suffix == +ve ones, discard & use default */ if ((nprefix_length != prefix_length) || (nsuffix_length != suffix_length) || ((nprefix_length > 0) && (xmlStrncmp(nprefix, prefix, prefix_length) !=0 )) || ((nsuffix_length > 0) && (xmlStrncmp(nsuffix, suffix, suffix_length) !=0 ))) { prefix = nprefix; prefix_length = nprefix_length; suffix = nsuffix; suffix_length = nsuffix_length; } /* else { default_sign = 1; } */ } } OUTPUT_NUMBER: if (found_error != 0) { xsltTransformError(NULL, NULL, NULL, "xsltFormatNumberConversion : " "error in format string '%s', using default\n", format); default_sign = (number < 0.0) ? 1 : 0; prefix_length = suffix_length = 0; format_info.integer_hash = 0; format_info.integer_digits = 1; format_info.frac_digits = 1; format_info.frac_hash = 4; format_info.group = -1; format_info.multiplier = 1; format_info.add_decimal = TRUE; } /* Ready to output our number. First see if "default sign" is required */ if (default_sign != 0) xmlBufferAdd(buffer, self->minusSign, xmlUTF8Strsize(self->minusSign, 1)); /* Put the prefix into the buffer */ for (j = 0; j < prefix_length; j++) { if ((pchar = *prefix++) == SYMBOL_QUOTE) { len = xmlUTF8Strsize(prefix, 1); xmlBufferAdd(buffer, prefix, len); prefix += len; j += len - 1; /* length of symbol less length of quote */ } else xmlBufferAdd(buffer, &pchar, 1); } /* Next do the integer part of the number */ number = fabs(number) * (double)format_info.multiplier; scale = pow(10.0, (double)(format_info.frac_digits + format_info.frac_hash)); number = floor((scale * number + 0.5)) / scale; if ((self->grouping != NULL) && (self->grouping[0] != 0)) { len = xmlStrlen(self->grouping); pchar = xsltGetUTF8Char(self->grouping, &len); xsltNumberFormatDecimal(buffer, floor(number), self->zeroDigit[0], format_info.integer_digits, format_info.group, pchar, len); } else xsltNumberFormatDecimal(buffer, floor(number), self->zeroDigit[0], format_info.integer_digits, format_info.group, ',', 1); /* Special case: java treats '.#' like '.0', '.##' like '.0#', etc. */ if ((format_info.integer_digits + format_info.integer_hash + format_info.frac_digits == 0) && (format_info.frac_hash > 0)) { ++format_info.frac_digits; --format_info.frac_hash; } /* Add leading zero, if required */ if ((floor(number) == 0) && (format_info.integer_digits + format_info.frac_digits == 0)) { xmlBufferAdd(buffer, self->zeroDigit, xmlUTF8Strsize(self->zeroDigit, 1)); } /* Next the fractional part, if required */ if (format_info.frac_digits + format_info.frac_hash == 0) { if (format_info.add_decimal) xmlBufferAdd(buffer, self->decimalPoint, xmlUTF8Strsize(self->decimalPoint, 1)); } else { number -= floor(number); if ((number != 0) || (format_info.frac_digits != 0)) { xmlBufferAdd(buffer, self->decimalPoint, xmlUTF8Strsize(self->decimalPoint, 1)); number = floor(scale * number + 0.5); for (j = format_info.frac_hash; j > 0; j--) { if (fmod(number, 10.0) >= 1.0) break; /* for */ number /= 10.0; } xsltNumberFormatDecimal(buffer, floor(number), self->zeroDigit[0], format_info.frac_digits + j, 0, 0, 0); } } /* Put the suffix into the buffer */ for (j = 0; j < suffix_length; j++) { if ((pchar = *suffix++) == SYMBOL_QUOTE) { len = xmlUTF8Strsize(suffix, 1); xmlBufferAdd(buffer, suffix, len); suffix += len; j += len - 1; /* length of symbol less length of escape */ } else xmlBufferAdd(buffer, &pchar, 1); } *result = xmlStrdup(xmlBufferContent(buffer)); xmlBufferFree(buffer); return status; }
/// Lookup the pair "char1", "char2" in the digraph tables. /// /// @param char1 /// @param char2 /// @param meta_char /// /// @return If no match, return "char2". If "meta_char" is TRUE and "char1" // is a space, return "char2" | 0x80. static int getexactdigraph(int char1, int char2, int meta_char) { int retval = 0; if (IS_SPECIAL(char1) || IS_SPECIAL(char2)) { return char2; } // Search user digraphs first. digr_T *dp = (digr_T *)user_digraphs.ga_data; for (int i = 0; i < user_digraphs.ga_len; ++i) { if (((int) dp->char1 == char1) && ((int) dp->char2 == char2)) { retval = dp->result; break; } ++dp; } // Search default digraphs. if (retval == 0) { dp = digraphdefault; for (int i = 0; dp->char1 != 0; ++i) { if (((int) dp->char1 == char1) && ((int) dp->char2 == char2)) { retval = dp->result; break; } ++dp; } } if ((retval != 0) && !enc_utf8) { char_u buf[6], *to; vimconv_T vc; // Convert the Unicode digraph to 'encoding'. int i = utf_char2bytes(retval, buf); retval = 0; vc.vc_type = CONV_NONE; if (convert_setup(&vc, (char_u *)"utf-8", p_enc) == OK) { vc.vc_fail = true; assert(i >= 0); size_t len = (size_t)i; to = string_convert(&vc, buf, &len); if (to != NULL) { retval = (*mb_ptr2char)(to); xfree(to); } (void)convert_setup(&vc, NULL, NULL); } } // Ignore multi-byte characters when not in multi-byte mode. if (!has_mbyte && (retval > 0xff)) { retval = 0; } if (retval == 0) { // digraph deleted or not found if ((char1 == ' ') && meta_char) { // <space> <char> --> meta-char return char2 | 0x80; } return char2; } return retval; }
/* If we have a --backup-dir, then we get here from make_backup(). * We will move the file to be deleted into a parallel directory tree. */ static int keep_backup(const char *fname) { stat_x sx; struct file_struct *file; char *buf; int save_preserve_xattrs = preserve_xattrs; int kept = 0; int ret_code; /* return if no file to keep */ if (x_lstat(fname, &sx.st, NULL) < 0) return 1; #ifdef SUPPORT_ACLS sx.acc_acl = sx.def_acl = NULL; #endif #ifdef SUPPORT_XATTRS sx.xattr = NULL; #endif if (!(file = make_file(fname, NULL, NULL, 0, NO_FILTERS))) return 1; /* the file could have disappeared */ if (!(buf = get_backup_name(fname))) { unmake_file(file); #ifdef SUPPORT_ACLS uncache_tmp_acls(); #endif #ifdef SUPPORT_XATTRS uncache_tmp_xattrs(); #endif return 0; } #ifdef SUPPORT_ACLS if (preserve_acls && !S_ISLNK(file->mode)) { get_acl(fname, &sx); cache_tmp_acl(file, &sx); free_acl(&sx); } #endif #ifdef SUPPORT_XATTRS if (preserve_xattrs) { get_xattr(fname, &sx); cache_tmp_xattr(file, &sx); free_xattr(&sx); } #endif /* Check to see if this is a device file, or link */ if ((am_root && preserve_devices && IS_DEVICE(file->mode)) || (preserve_specials && IS_SPECIAL(file->mode))) { int save_errno; do_unlink(buf); if (do_mknod(buf, file->mode, sx.st.st_rdev) < 0) { save_errno = errno ? errno : EINVAL; /* 0 paranoia */ if (errno == ENOENT && make_bak_dir(buf) == 0) { if (do_mknod(buf, file->mode, sx.st.st_rdev) < 0) save_errno = errno ? errno : save_errno; else save_errno = 0; } if (save_errno) { rsyserr(FERROR, save_errno, "mknod %s failed", full_fname(buf)); } } else save_errno = 0; if (verbose > 2 && save_errno == 0) { rprintf(FINFO, "make_backup: DEVICE %s successful.\n", fname); } kept = 1; do_unlink(fname); } if (!kept && S_ISDIR(file->mode)) { /* make an empty directory */ if (do_mkdir(buf, file->mode) < 0) { int save_errno = errno ? errno : EINVAL; /* 0 paranoia */ if (errno == ENOENT && make_bak_dir(buf) == 0) { if (do_mkdir(buf, file->mode) < 0) save_errno = errno ? errno : save_errno; else save_errno = 0; } if (save_errno) { rsyserr(FINFO, save_errno, "mkdir %s failed", full_fname(buf)); } } ret_code = do_rmdir(fname); if (verbose > 2) { rprintf(FINFO, "make_backup: RMDIR %s returns %i\n", full_fname(fname), ret_code); } kept = 1; } #ifdef SUPPORT_LINKS if (!kept && preserve_links && S_ISLNK(file->mode)) { const char *sl = F_SYMLINK(file); if (safe_symlinks && unsafe_symlink(sl, fname)) { if (verbose) { rprintf(FINFO, "ignoring unsafe symlink %s -> %s\n", full_fname(buf), sl); } kept = 1; } else { do_unlink(buf); if (do_symlink(sl, buf) < 0) { int save_errno = errno ? errno : EINVAL; /* 0 paranoia */ if (errno == ENOENT && make_bak_dir(buf) == 0) { if (do_symlink(sl, buf) < 0) save_errno = errno ? errno : save_errno; else save_errno = 0; } if (save_errno) { rsyserr(FERROR, save_errno, "link %s -> \"%s\"", full_fname(buf), sl); } } do_unlink(fname); kept = 1; } } #endif if (!kept && !S_ISREG(file->mode)) { rprintf(FINFO, "make_bak: skipping non-regular file %s\n", fname); unmake_file(file); #ifdef SUPPORT_ACLS uncache_tmp_acls(); #endif #ifdef SUPPORT_XATTRS uncache_tmp_xattrs(); #endif return 1; } /* move to keep tree if a file */ if (!kept) { if (robust_move(fname, buf) != 0) { rsyserr(FERROR, errno, "keep_backup failed: %s -> \"%s\"", full_fname(fname), buf); } else if (sx.st.st_nlink > 1) { /* If someone has hard-linked the file into the backup * dir, rename() might return success but do nothing! */ robust_unlink(fname); /* Just in case... */ } } preserve_xattrs = 0; set_file_attrs(buf, file, NULL, fname, 0); preserve_xattrs = save_preserve_xattrs; unmake_file(file); #ifdef SUPPORT_ACLS uncache_tmp_acls(); #endif #ifdef SUPPORT_XATTRS uncache_tmp_xattrs(); #endif if (verbose > 1) { rprintf(FINFO, "backed up %s to %s\n", fname, buf); } return 1; }
/* Hard-link, rename, or copy an item to the backup name. Returns 0 for * failure, 1 if item was moved, 2 if item was duplicated or hard linked * into backup area, or 3 if item doesn't exist or isn't a regular file. */ int make_backup(const char *fname, BOOL prefer_rename) { stat_x sx; struct file_struct *file; int save_preserve_xattrs; char *buf; int ret = 0; init_stat_x(&sx); /* Return success if no file to keep. */ if (x_lstat(fname, &sx.st, NULL) < 0) return 3; if (!(buf = get_backup_name(fname))) return 0; /* Try a hard-link or a rename first. Using rename is not atomic, but * is more efficient than forcing a copy for larger files when no hard- * linking is possible. */ if ((ret = link_or_rename(fname, buf, prefer_rename, &sx.st)) != 0) goto success; if (errno == EEXIST || errno == EISDIR) { STRUCT_STAT bakst; if (do_lstat(buf, &bakst) == 0) { int flags = get_del_for_flag(bakst.st_mode) | DEL_FOR_BACKUP | DEL_RECURSE; if (delete_item(buf, bakst.st_mode, flags) != 0) return 0; } if ((ret = link_or_rename(fname, buf, prefer_rename, &sx.st)) != 0) goto success; } /* Fall back to making a copy. */ if (!(file = make_file(fname, NULL, &sx.st, 0, NO_FILTERS))) return 3; /* the file could have disappeared */ #ifdef SUPPORT_ACLS if (preserve_acls && !S_ISLNK(file->mode)) { get_acl(fname, &sx); cache_tmp_acl(file, &sx); free_acl(&sx); } #endif #ifdef SUPPORT_XATTRS if (preserve_xattrs) { get_xattr(fname, &sx); cache_tmp_xattr(file, &sx); free_xattr(&sx); } #endif /* Check to see if this is a device file, or link */ if ((am_root && preserve_devices && IS_DEVICE(file->mode)) || (preserve_specials && IS_SPECIAL(file->mode))) { if (do_mknod(buf, file->mode, sx.st.st_rdev) < 0) rsyserr(FERROR, errno, "mknod %s failed", full_fname(buf)); else if (DEBUG_GTE(BACKUP, 1)) rprintf(FINFO, "make_backup: DEVICE %s successful.\n", fname); ret = 2; } #ifdef SUPPORT_LINKS if (!ret && preserve_links && S_ISLNK(file->mode)) { const char *sl = F_SYMLINK(file); if (safe_symlinks && unsafe_symlink(sl, fname)) { if (INFO_GTE(SYMSAFE, 1)) { rprintf(FINFO, "not backing up unsafe symlink \"%s\" -> \"%s\"\n", fname, sl); } ret = 2; } else { if (do_symlink(sl, buf) < 0) rsyserr(FERROR, errno, "link %s -> \"%s\"", full_fname(buf), sl); else if (DEBUG_GTE(BACKUP, 1)) rprintf(FINFO, "make_backup: SYMLINK %s successful.\n", fname); ret = 2; } } #endif if (!ret && !S_ISREG(file->mode)) { rprintf(FINFO, "make_bak: skipping non-regular file %s\n", fname); unmake_file(file); #ifdef SUPPORT_ACLS uncache_tmp_acls(); #endif #ifdef SUPPORT_XATTRS uncache_tmp_xattrs(); #endif return 3; } /* Copy to backup tree if a file. */ if (!ret) { if (copy_file(fname, buf, -1, file->mode) < 0) { rsyserr(FERROR, errno, "keep_backup failed: %s -> \"%s\"", full_fname(fname), buf); unmake_file(file); #ifdef SUPPORT_ACLS uncache_tmp_acls(); #endif #ifdef SUPPORT_XATTRS uncache_tmp_xattrs(); #endif return 0; } if (DEBUG_GTE(BACKUP, 1)) rprintf(FINFO, "make_backup: COPY %s successful.\n", fname); ret = 2; } save_preserve_xattrs = preserve_xattrs; preserve_xattrs = 0; set_file_attrs(buf, file, NULL, fname, ATTRS_SET_NANO); preserve_xattrs = save_preserve_xattrs; unmake_file(file); #ifdef SUPPORT_ACLS uncache_tmp_acls(); #endif #ifdef SUPPORT_XATTRS uncache_tmp_xattrs(); #endif success: if (INFO_GTE(BACKUP, 1)) rprintf(FINFO, "backed up %s to %s\n", fname, buf); return ret; }
void nextToken(FILE *input) { char buffer[FN_NAME_MAX + 1]; int c; for (c = fgetc(input); IS_WHITESPACE(c); c = fgetc(input)); if (c == EOF) { #ifdef DEBUG printf("Got EOF\n"); #endif die("EOF Reached"); } if (c == '(') { lookahead.type = BEGIN; #ifdef DEBUG printf("Got (\n"); #endif } else if (c == ')') { lookahead.type = END; #ifdef DEBUG printf("Got )\n"); #endif } else if (IS_SIGN_PREFIX(c) && isdigit(fpeek(input)) || isdigit(c)) { ungetc(c, input); lookahead.type = VALUE; fscanf(input, "%lf", &lookahead.value.number); #ifdef DEBUG printf("Got number %f\n", lookahead.value.number); #endif } else { unsigned pos = 1; int index; lookahead.type = FUNCTION; buffer[0] = c & 0xFF; memset(buffer + 1, '\0', FN_NAME_MAX); c = fgetc(input); while (!IS_SPECIAL(c) && pos < FN_NAME_MAX) { buffer[pos++] = c & 0xFF; c = fgetc(input); } if (pos == FN_NAME_MAX && !IS_SPECIAL(c)) die("token too long"); ungetc(c, input); index = lookupFunction(buffer); if (index < 0) die("function not found"); else lookahead.value.fnIndex = index; #ifdef DEBUG printf("Got function: %d:%s\n", lookahead.value.fnIndex, buffer); #endif } }
/* A generic logging routine for send/recv, with parameter substitiution. */ static void log_formatted(enum logcode code, const char *format, const char *op, struct file_struct *file, const char *fname, int iflags, const char *hlink) { char buf[MAXPATHLEN+1024], buf2[MAXPATHLEN], fmt[32]; char *p, *s, *c; const char *n; size_t len, total; int64 b; *fmt = '%'; /* We expand % codes one by one in place in buf. We don't * copy in the terminating null of the inserted strings, but * rather keep going until we reach the null of the format. */ total = strlcpy(buf, format, sizeof buf); if (total > MAXPATHLEN) { rprintf(FERROR, "log-format string is WAY too long!\n"); exit_cleanup(RERR_MESSAGEIO); } buf[total++] = '\n'; buf[total] = '\0'; for (p = buf; (p = strchr(p, '%')) != NULL; ) { int humanize = 0; s = p++; c = fmt + 1; while (*p == '\'') { humanize++; p++; } if (*p == '-') *c++ = *p++; while (isDigit(p) && c - fmt < (int)(sizeof fmt) - 8) *c++ = *p++; while (*p == '\'') { humanize++; p++; } if (!*p) break; *c = '\0'; n = NULL; /* Note for %h and %a: it doesn't matter what fd we pass to * client_{name,addr} because rsync_module will already have * forced the answer to be cached (assuming, of course, for %h * that lp_reverse_lookup(module_id) is true). */ switch (*p) { case 'h': if (am_daemon) { n = lp_reverse_lookup(module_id) ? client_name(0) : undetermined_hostname; } break; case 'a': if (am_daemon) n = client_addr(0); break; case 'l': strlcat(fmt, "s", sizeof fmt); snprintf(buf2, sizeof buf2, fmt, do_big_num(F_LENGTH(file), humanize, NULL)); n = buf2; break; case 'U': strlcat(fmt, "u", sizeof fmt); snprintf(buf2, sizeof buf2, fmt, uid_ndx ? F_OWNER(file) : 0); n = buf2; break; case 'G': if (!gid_ndx || file->flags & FLAG_SKIP_GROUP) n = "DEFAULT"; else { strlcat(fmt, "u", sizeof fmt); snprintf(buf2, sizeof buf2, fmt, F_GROUP(file)); n = buf2; } break; case 'p': strlcat(fmt, "d", sizeof fmt); snprintf(buf2, sizeof buf2, fmt, (int)getpid()); n = buf2; break; case 'M': n = c = timestring(file->modtime); while ((c = strchr(c, ' ')) != NULL) *c = '-'; break; case 'B': c = buf2 + MAXPATHLEN - PERMSTRING_SIZE - 1; permstring(c, file->mode); n = c + 1; /* skip the type char */ break; case 'o': n = op; break; case 'f': if (fname) { c = f_name_buf(); strlcpy(c, fname, MAXPATHLEN); } else c = f_name(file, NULL); if (am_sender && F_PATHNAME(file)) { pathjoin(buf2, sizeof buf2, F_PATHNAME(file), c); clean_fname(buf2, 0); if (fmt[1]) { strlcpy(c, buf2, MAXPATHLEN); n = c; } else n = buf2; } else if (am_daemon && *c != '/') { pathjoin(buf2, sizeof buf2, curr_dir + module_dirlen, c); clean_fname(buf2, 0); if (fmt[1]) { strlcpy(c, buf2, MAXPATHLEN); n = c; } else n = buf2; } else { clean_fname(c, 0); n = c; } if (*n == '/') n++; break; case 'n': if (fname) { c = f_name_buf(); strlcpy(c, fname, MAXPATHLEN); } else c = f_name(file, NULL); if (S_ISDIR(file->mode)) strlcat(c, "/", MAXPATHLEN); n = c; break; case 'L': if (hlink && *hlink) { n = hlink; strlcpy(buf2, " => ", sizeof buf2); } else if (S_ISLNK(file->mode) && !fname) { n = F_SYMLINK(file); strlcpy(buf2, " -> ", sizeof buf2); } else { n = ""; if (!fmt[1]) break; strlcpy(buf2, " ", sizeof buf2); } strlcat(fmt, "s", sizeof fmt); snprintf(buf2 + 4, sizeof buf2 - 4, fmt, n); n = buf2; break; case 'm': n = lp_name(module_id); break; case 't': n = timestring(time(NULL)); break; case 'P': n = full_module_path; break; case 'u': n = auth_user; break; case 'b': case 'c': if (!(iflags & ITEM_TRANSFER)) b = 0; else if ((!!am_sender) ^ (*p == 'c')) b = total_data_written - initial_data_written; else b = total_data_read - initial_data_read; strlcat(fmt, "s", sizeof fmt); snprintf(buf2, sizeof buf2, fmt, do_big_num(b, humanize, NULL)); n = buf2; break; case 'C': n = NULL; if (S_ISREG(file->mode)) { if (always_checksum && canonical_checksum(checksum_type)) n = sum_as_hex(checksum_type, F_SUM(file)); else if (iflags & ITEM_TRANSFER && canonical_checksum(xfersum_type)) n = sum_as_hex(xfersum_type, sender_file_sum); } if (!n) { int checksum_len = csum_len_for_type(always_checksum ? checksum_type : xfersum_type); memset(buf2, ' ', checksum_len*2); buf2[checksum_len*2] = '\0'; n = buf2; } break; case 'i': if (iflags & ITEM_DELETED) { n = "*deleting "; break; } n = c = buf2 + MAXPATHLEN - 32; c[0] = iflags & ITEM_LOCAL_CHANGE ? iflags & ITEM_XNAME_FOLLOWS ? 'h' : 'c' : !(iflags & ITEM_TRANSFER) ? '.' : !local_server && *op == 's' ? '<' : '>'; if (S_ISLNK(file->mode)) { c[1] = 'L'; c[3] = '.'; c[4] = !(iflags & ITEM_REPORT_TIME) ? '.' : !preserve_times || !receiver_symlink_times || (iflags & ITEM_REPORT_TIMEFAIL) ? 'T' : 't'; } else { c[1] = S_ISDIR(file->mode) ? 'd' : IS_SPECIAL(file->mode) ? 'S' : IS_DEVICE(file->mode) ? 'D' : 'f'; c[3] = !(iflags & ITEM_REPORT_SIZE) ? '.' : 's'; c[4] = !(iflags & ITEM_REPORT_TIME) ? '.' : !preserve_times ? 'T' : 't'; } c[2] = !(iflags & ITEM_REPORT_CHANGE) ? '.' : 'c'; c[5] = !(iflags & ITEM_REPORT_PERMS) ? '.' : 'p'; c[6] = !(iflags & ITEM_REPORT_OWNER) ? '.' : 'o'; c[7] = !(iflags & ITEM_REPORT_GROUP) ? '.' : 'g'; c[8] = !(iflags & ITEM_REPORT_ATIME) ? '.' : 'u'; c[9] = !(iflags & ITEM_REPORT_ACL) ? '.' : 'a'; c[10] = !(iflags & ITEM_REPORT_XATTR) ? '.' : 'x'; c[11] = '\0'; if (iflags & (ITEM_IS_NEW|ITEM_MISSING_DATA)) { char ch = iflags & ITEM_IS_NEW ? '+' : '?'; int i; for (i = 2; c[i]; i++) c[i] = ch; } else if (c[0] == '.' || c[0] == 'h' || c[0] == 'c') { int i; for (i = 2; c[i]; i++) { if (c[i] != '.') break; } if (!c[i]) { for (i = 2; c[i]; i++) c[i] = ' '; } } break; } /* "n" is the string to be inserted in place of this % code. */ if (!n) continue; if (n != buf2 && fmt[1]) { strlcat(fmt, "s", sizeof fmt); snprintf(buf2, sizeof buf2, fmt, n); n = buf2; } len = strlen(n); /* Subtract the length of the escape from the string's size. */ total -= p - s + 1; if (len + total >= (size_t)sizeof buf) { rprintf(FERROR, "buffer overflow expanding %%%c -- exiting\n", p[0]); exit_cleanup(RERR_MESSAGEIO); } /* Shuffle the rest of the string along to make space for n */ if (len != (size_t)(p - s + 1)) memmove(s + len, p + 1, total - (s - buf) + 1); total += len; /* Insert the contents of string "n", but NOT its null. */ if (len) memcpy(s, n, len); /* Skip over inserted string; continue looking */ p = s + len; } rwrite(code, buf, total, 0); }
/// Map Farsi keyboard when in fkmap mode. int fkmap(int c) { int tempc; static int revins; if (IS_SPECIAL(c)) { return c; } if (VIM_ISDIGIT(c) || (((c == '.') || (c == '+') || (c == '-') || (c == '^') || (c == '%') || (c == '#') || (c == '=')) && revins)) { if (!revins) { if (curwin->w_cursor.col) { if (!p_ri) { dec_cursor(); } chg_c_toX_orX(); chg_l_toXor_X(); if (!p_ri) { inc_cursor(); } } } arrow_used = TRUE; (void)stop_arrow(); if (!curwin->w_p_rl && revins) { inc_cursor(); } revins++; p_ri = 1; } else { if (revins) { arrow_used = TRUE; (void)stop_arrow(); revins = 0; if (curwin->w_p_rl) { while ((F_isdigit(gchar_cursor()) || (gchar_cursor() == F_PERIOD || gchar_cursor() == F_PLUS || gchar_cursor() == F_MINUS || gchar_cursor() == F_MUL || gchar_cursor() == F_DIVIDE || gchar_cursor() == F_PERCENT || gchar_cursor() == F_EQUALS)) && gchar_cursor() != '\0') { curwin->w_cursor.col++; } } else { if (curwin->w_cursor.col) { while ((F_isdigit(gchar_cursor()) || (gchar_cursor() == F_PERIOD || gchar_cursor() == F_PLUS || gchar_cursor() == F_MINUS || gchar_cursor() == F_MUL || gchar_cursor() == F_DIVIDE || gchar_cursor() == F_PERCENT || gchar_cursor() == F_EQUALS)) && --curwin->w_cursor.col) { } } if (!F_isdigit(gchar_cursor())) { ++curwin->w_cursor.col; } } } } if (!revins) { if (curwin->w_p_rl) { p_ri = 0; } if (!curwin->w_p_rl) { p_ri = 1; } } if ((c < 0x100) && (isalpha(c) || (c == '&') || (c == '^') || (c == ';') || (c == '\'') || (c == ',') || (c == '[') || (c == ']') || (c == '{') || (c == '}'))) { chg_r_to_Xor_X_(); } tempc = 0; switch (c) { case '`': case ' ': case '.': case '!': case '"': case '$': case '%': case '^': case '&': case '/': case '(': case ')': case '=': case '\\': case '?': case '+': case '-': case '_': case '*': case ':': case '#': case '~': case '@': case '<': case '>': case '{': case '}': case '|': case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': case 'B': case 'E': case 'F': case 'H': case 'I': case 'K': case 'L': case 'M': case 'O': case 'P': case 'Q': case 'R': case 'T': case 'U': case 'W': case 'Y': case NL: case TAB: if (p_ri && (c == NL) && curwin->w_cursor.col) { // If the char before the cursor is _X_ or X_ do not change // the one under the cursor with X type. dec_cursor(); if (F_isalpha(gchar_cursor())) { inc_cursor(); return NL; } inc_cursor(); } if (!p_ri) { if (!curwin->w_cursor.col) { switch (c) { case '0': return FARSI_0; case '1': return FARSI_1; case '2': return FARSI_2; case '3': return FARSI_3; case '4': return FARSI_4; case '5': return FARSI_5; case '6': return FARSI_6; case '7': return FARSI_7; case '8': return FARSI_8; case '9': return FARSI_9; case 'B': return F_PSP; case 'E': return JAZR_N; case 'F': return ALEF_D_H; case 'H': return ALEF_A; case 'I': return TASH; case 'K': return F_LQUOT; case 'L': return F_RQUOT; case 'M': return HAMZE; case 'O': return '['; case 'P': return ']'; case 'Q': return OO; case 'R': return MAD_N; case 'T': return OW; case 'U': return MAD; case 'W': return OW_OW; case 'Y': return JAZR; case '`': return F_PCN; case '!': return F_EXCL; case '@': return F_COMMA; case '#': return F_DIVIDE; case '$': return F_CURRENCY; case '%': return F_PERCENT; case '^': return F_MUL; case '&': return F_BCOMMA; case '*': return F_STAR; case '(': return F_LPARENT; case ')': return F_RPARENT; case '-': return F_MINUS; case '_': return F_UNDERLINE; case '=': return F_EQUALS; case '+': return F_PLUS; case '\\': return F_BSLASH; case '|': return F_PIPE; case ':': return F_DCOLON; case '"': return F_SEMICOLON; case '.': return F_PERIOD; case '/': return F_SLASH; case '<': return F_LESS; case '>': return F_GREATER; case '?': return F_QUESTION; case ' ': return F_BLANK; } break; } } if (!p_ri) { dec_cursor(); } switch ((tempc = gchar_cursor())) { case _BE: case _PE: case _TE: case _SE: case _JIM: case _CHE: case _HE_J: case _XE: case _SIN: case _SHIN: case _SAD: case _ZAD: case _FE: case _GHAF: case _KAF: case _KAF_H: case _GAF: case _LAM: case _MIM: case _NOON: case _HE: case _HE_: case _TA: case _ZA: put_curr_and_l_to_X(toF_TyA(tempc)); break; case _AYN: case _AYN_: if (!p_ri) { if (!curwin->w_cursor.col) { put_curr_and_l_to_X(AYN); break; } } if (p_ri) { inc_cursor(); } else { dec_cursor(); } if (F_is_TyB_TyC_TyD(SRC_EDT, AT_CURSOR)) { tempc = AYN_; } else { tempc = AYN; } if (p_ri) { dec_cursor(); } else { inc_cursor(); } put_curr_and_l_to_X(tempc); break; case _GHAYN: case _GHAYN_: if (!p_ri) { if (!curwin->w_cursor.col) { put_curr_and_l_to_X(GHAYN); break; } } if (p_ri) { inc_cursor(); } else { dec_cursor(); } if (F_is_TyB_TyC_TyD(SRC_EDT, AT_CURSOR)) { tempc = GHAYN_; } else { tempc = GHAYN; } if (p_ri) { dec_cursor(); } else { inc_cursor(); } put_curr_and_l_to_X(tempc); break; case _YE: case _IE: case _YEE: if (!p_ri) { if (!curwin->w_cursor.col) { put_curr_and_l_to_X((tempc == _YE ? YE : (tempc == _IE ? IE : YEE))); break; } } if (p_ri) { inc_cursor(); } else { dec_cursor(); } if (F_is_TyB_TyC_TyD(SRC_EDT, AT_CURSOR)) { tempc = (tempc == _YE ? YE_ : (tempc == _IE ? IE_ : YEE_)); } else { tempc = (tempc == _YE ? YE : (tempc == _IE ? IE : YEE)); } if (p_ri) { dec_cursor(); } else { inc_cursor(); } put_curr_and_l_to_X(tempc); break; } if (!p_ri) { inc_cursor(); } tempc = 0; switch (c) { case '0': return FARSI_0; case '1': return FARSI_1; case '2': return FARSI_2; case '3': return FARSI_3; case '4': return FARSI_4; case '5': return FARSI_5; case '6': return FARSI_6; case '7': return FARSI_7; case '8': return FARSI_8; case '9': return FARSI_9; case 'B': return F_PSP; case 'E': return JAZR_N; case 'F': return ALEF_D_H; case 'H': return ALEF_A; case 'I': return TASH; case 'K': return F_LQUOT; case 'L': return F_RQUOT; case 'M': return HAMZE; case 'O': return '['; case 'P': return ']'; case 'Q': return OO; case 'R': return MAD_N; case 'T': return OW; case 'U': return MAD; case 'W': return OW_OW; case 'Y': return JAZR; case '`': return F_PCN; case '!': return F_EXCL; case '@': return F_COMMA; case '#': return F_DIVIDE; case '$': return F_CURRENCY; case '%': return F_PERCENT; case '^': return F_MUL; case '&': return F_BCOMMA; case '*': return F_STAR; case '(': return F_LPARENT; case ')': return F_RPARENT; case '-': return F_MINUS; case '_': return F_UNDERLINE; case '=': return F_EQUALS; case '+': return F_PLUS; case '\\': return F_BSLASH; case '|': return F_PIPE; case ':': return F_DCOLON; case '"': return F_SEMICOLON; case '.': return F_PERIOD; case '/': return F_SLASH; case '<': return F_LESS; case '>': return F_GREATER; case '?': return F_QUESTION; case ' ': return F_BLANK; } break; case 'a': tempc = _SHIN; break; case 'A': tempc = WAW_H; break; case 'b': tempc = ZAL; break; case 'c': tempc = ZE; break; case 'C': tempc = JE; break; case 'd': tempc = _YE; break; case 'D': tempc = _YEE; break; case 'e': tempc = _SE; break; case 'f': tempc = _BE; break; case 'g': tempc = _LAM; break; case 'G': if (!curwin->w_cursor.col && STRLEN(ml_get_curline())) { if (gchar_cursor() == _LAM) { chg_c_toX_orX(); } else if (p_ri) { chg_c_to_X_or_X(); } } if (!p_ri) { if (!curwin->w_cursor.col) { return ALEF_U_H; } } if (!p_ri) { dec_cursor(); } if (gchar_cursor() == _LAM) { chg_c_toX_orX(); chg_l_toXor_X(); tempc = ALEF_U_H; } else if (F_is_TyB_TyC_TyD(SRC_EDT, AT_CURSOR)) { tempc = ALEF_U_H_; chg_l_toXor_X(); } else { tempc = ALEF_U_H; } if (!p_ri) { inc_cursor(); } return tempc; case 'h': if (!curwin->w_cursor.col && STRLEN(ml_get_curline())) { if (p_ri) { chg_c_to_X_or_X(); } } if (!p_ri) { if (!curwin->w_cursor.col) { return ALEF; } } if (!p_ri) { dec_cursor(); } if (gchar_cursor() == _LAM) { chg_l_toXor_X(); del_char(FALSE); AppendCharToRedobuff(K_BS); if (!p_ri) { dec_cursor(); } tempc = LA; } else { if (F_is_TyB_TyC_TyD(SRC_EDT, AT_CURSOR)) { tempc = ALEF_; chg_l_toXor_X(); } else { tempc = ALEF; } } if (!p_ri) { inc_cursor(); } return tempc; case 'i': if (!curwin->w_cursor.col && STRLEN(ml_get_curline())) { if (!p_ri && !F_is_TyE(tempc)) { chg_c_to_X_orX_(); } if (p_ri) { chg_c_to_X_or_X(); } } if (!p_ri && !curwin->w_cursor.col) { return _HE; } if (!p_ri) { dec_cursor(); } if (F_is_TyB_TyC_TyD(SRC_EDT, AT_CURSOR)) { tempc = _HE_; } else { tempc = _HE; } if (!p_ri) { inc_cursor(); } break; case 'j': tempc = _TE; break; case 'J': if (!curwin->w_cursor.col && STRLEN(ml_get_curline())) { if (p_ri) { chg_c_to_X_or_X(); } } if (!p_ri) { if (!curwin->w_cursor.col) { return TEE; } } if (!p_ri) { dec_cursor(); } if (F_is_TyB_TyC_TyD(SRC_EDT, AT_CURSOR)) { tempc = TEE_; chg_l_toXor_X(); } else { tempc = TEE; } if (!p_ri) { inc_cursor(); } return tempc; case 'k': tempc = _NOON; break; case 'l': tempc = _MIM; break; case 'm': tempc = _PE; break; case 'n': case 'N': tempc = DAL; break; case 'o': tempc = _XE; break; case 'p': tempc = _HE_J; break; case 'q': tempc = _ZAD; break; case 'r': tempc = _GHAF; break; case 's': tempc = _SIN; break; case 'S': tempc = _IE; break; case 't': tempc = _FE; break; case 'u': if (!curwin->w_cursor.col && STRLEN(ml_get_curline())) { if (!p_ri && !F_is_TyE(tempc)) { chg_c_to_X_orX_(); } if (p_ri) { chg_c_to_X_or_X(); } } if (!p_ri && !curwin->w_cursor.col) { return _AYN; } if (!p_ri) { dec_cursor(); } if (F_is_TyB_TyC_TyD(SRC_EDT, AT_CURSOR)) { tempc = _AYN_; } else { tempc = _AYN; } if (!p_ri) { inc_cursor(); } break; case 'v': case 'V': tempc = RE; break; case 'w': tempc = _SAD; break; case 'x': case 'X': tempc = _TA; break; case 'y': if (!curwin->w_cursor.col && STRLEN(ml_get_curline())) { if (!p_ri && !F_is_TyE(tempc)) { chg_c_to_X_orX_(); } if (p_ri) { chg_c_to_X_or_X(); } } if (!p_ri && !curwin->w_cursor.col) { return _GHAYN; } if (!p_ri) { dec_cursor(); } if (F_is_TyB_TyC_TyD(SRC_EDT, AT_CURSOR)) { tempc = _GHAYN_; } else { tempc = _GHAYN; } if (!p_ri) { inc_cursor(); } break; case 'z': tempc = _ZA; break; case 'Z': tempc = _KAF_H; break; case ';': tempc = _KAF; break; case '\'': tempc = _GAF; break; case ',': tempc = WAW; break; case '[': tempc = _JIM; break; case ']': tempc = _CHE; break; } if ((F_isalpha(tempc) || F_isdigit(tempc))) { if (!curwin->w_cursor.col && STRLEN(ml_get_curline())) { if (!p_ri && !F_is_TyE(tempc)) { chg_c_to_X_orX_(); } if (p_ri) { chg_c_to_X_or_X(); } } if (curwin->w_cursor.col) { if (!p_ri) { dec_cursor(); } if (F_is_TyE(tempc)) { chg_l_toXor_X(); } else { chg_l_to_X_orX_(); } if (!p_ri) { inc_cursor(); } } } if (tempc) { return tempc; } return c; }