X-Git-Url: http://git.chise.org/gitweb/?a=blobdiff_plain;f=src%2Ffile-coding.c;h=fe42ebdf0b4869793638f3c05bed93f9491908fd;hb=79d2db7d65205bc85d471590726d0cf3af5598e0;hp=c6e9ae0f61c7639abe01b27162097f5cc210da7a;hpb=ea1ea793fe6e244ef5555ed983423a204101af13;p=chise%2Fxemacs-chise.git.1 diff --git a/src/file-coding.c b/src/file-coding.c index c6e9ae0..fe42ebd 100644 --- a/src/file-coding.c +++ b/src/file-coding.c @@ -30,6 +30,7 @@ Boston, MA 02111-1307, USA. */ #include "elhash.h" #include "insdel.h" #include "lstream.h" +#include "opaque.h" #ifdef MULE #include "mule-ccl.h" #include "chartab.h" @@ -45,29 +46,33 @@ Lisp_Object Vcoding_system_for_write; Lisp_Object Vfile_name_coding_system; /* Table of symbols identifying each coding category. */ -Lisp_Object coding_category_symbol[CODING_CATEGORY_LAST + 1]; +Lisp_Object coding_category_symbol[CODING_CATEGORY_LAST]; struct file_coding_dump { /* Coding system currently associated with each coding category. */ - Lisp_Object coding_category_system[CODING_CATEGORY_LAST + 1]; + Lisp_Object coding_category_system[CODING_CATEGORY_LAST]; /* Table of all coding categories in decreasing order of priority. This describes a permutation of the possible coding categories. */ - int coding_category_by_priority[CODING_CATEGORY_LAST + 1]; + int coding_category_by_priority[CODING_CATEGORY_LAST]; +#ifdef MULE Lisp_Object ucs_to_mule_table[65536]; +#endif } *fcd; static const struct lrecord_description fcd_description_1[] = { - { XD_LISP_OBJECT, offsetof(struct file_coding_dump, coding_category_system), CODING_CATEGORY_LAST + 1 }, - { XD_LISP_OBJECT, offsetof(struct file_coding_dump, ucs_to_mule_table), 65536 }, + { XD_LISP_OBJECT_ARRAY, offsetof (struct file_coding_dump, coding_category_system), CODING_CATEGORY_LAST }, +#ifdef MULE + { XD_LISP_OBJECT_ARRAY, offsetof (struct file_coding_dump, ucs_to_mule_table), countof (fcd->ucs_to_mule_table) }, +#endif { XD_END } }; static const struct struct_description fcd_description = { - sizeof(struct file_coding_dump), + sizeof (struct file_coding_dump), fcd_description_1 }; @@ -92,7 +97,7 @@ Lisp_Object Qforce_g0_on_output, Qforce_g1_on_output; Lisp_Object Qforce_g2_on_output, Qforce_g3_on_output; Lisp_Object Qno_iso6429; Lisp_Object Qinput_charset_conversion, Qoutput_charset_conversion; -Lisp_Object Qctext, Qescape_quoted; +Lisp_Object Qescape_quoted; Lisp_Object Qshort, Qno_ascii_eol, Qno_ascii_cntl, Qseven, Qlock_shift; #endif Lisp_Object Qencode, Qdecode; @@ -171,68 +176,47 @@ EXFUN (Fcopy_coding_system, 2); #ifdef MULE struct detection_state; static int detect_coding_sjis (struct detection_state *st, - CONST unsigned char *src, - unsigned int n); -static void decode_coding_sjis (Lstream *decoding, - CONST unsigned char *src, - unsigned_char_dynarr *dst, - unsigned int n); -static void encode_coding_sjis (Lstream *encoding, - CONST unsigned char *src, - unsigned_char_dynarr *dst, - unsigned int n); + const Extbyte *src, Lstream_data_count n); +static void decode_coding_sjis (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); +static void encode_coding_sjis (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); static int detect_coding_big5 (struct detection_state *st, - CONST unsigned char *src, - unsigned int n); -static void decode_coding_big5 (Lstream *decoding, - CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n); -static void encode_coding_big5 (Lstream *encoding, - CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n); + const Extbyte *src, Lstream_data_count n); +static void decode_coding_big5 (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); +static void encode_coding_big5 (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); static int detect_coding_ucs4 (struct detection_state *st, - CONST unsigned char *src, - unsigned int n); -static void decode_coding_ucs4 (Lstream *decoding, - CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n); -static void encode_coding_ucs4 (Lstream *encoding, - CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n); + const Extbyte *src, Lstream_data_count n); +static void decode_coding_ucs4 (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); +static void encode_coding_ucs4 (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); static int detect_coding_utf8 (struct detection_state *st, - CONST unsigned char *src, - unsigned int n); -static void decode_coding_utf8 (Lstream *decoding, - CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n); -static void encode_coding_utf8 (Lstream *encoding, - CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n); + const Extbyte *src, Lstream_data_count n); +static void decode_coding_utf8 (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); +static void encode_coding_utf8 (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); static int postprocess_iso2022_mask (int mask); static void reset_iso2022 (Lisp_Object coding_system, struct iso2022_decoder *iso); static int detect_coding_iso2022 (struct detection_state *st, - CONST unsigned char *src, - unsigned int n); -static void decode_coding_iso2022 (Lstream *decoding, - CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n); -static void encode_coding_iso2022 (Lstream *encoding, - CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n); + const Extbyte *src, Lstream_data_count n); +static void decode_coding_iso2022 (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); +static void encode_coding_iso2022 (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); #endif /* MULE */ -static void decode_coding_no_conversion (Lstream *decoding, - CONST unsigned char *src, - unsigned_char_dynarr *dst, - unsigned int n); -static void encode_coding_no_conversion (Lstream *encoding, - CONST unsigned char *src, - unsigned_char_dynarr *dst, - unsigned int n); -static void mule_decode (Lstream *decoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n); -static void mule_encode (Lstream *encoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n); +static void decode_coding_no_conversion (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); +static void encode_coding_no_conversion (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); +static void mule_decode (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); +static void mule_encode (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n); typedef struct codesys_prop codesys_prop; struct codesys_prop @@ -247,22 +231,22 @@ typedef struct } codesys_prop_dynarr; static const struct lrecord_description codesys_prop_description_1[] = { - { XD_LISP_OBJECT, offsetof(codesys_prop, sym), 1 }, + { XD_LISP_OBJECT, offsetof (codesys_prop, sym) }, { XD_END } }; static const struct struct_description codesys_prop_description = { - sizeof(codesys_prop), + sizeof (codesys_prop), codesys_prop_description_1 }; static const struct lrecord_description codesys_prop_dynarr_description_1[] = { - XD_DYNARR_DESC(codesys_prop_dynarr, &codesys_prop_description), + XD_DYNARR_DESC (codesys_prop_dynarr, &codesys_prop_description), { XD_END } }; static const struct struct_description codesys_prop_dynarr_description = { - sizeof(codesys_prop_dynarr), + sizeof (codesys_prop_dynarr), codesys_prop_dynarr_description_1 }; @@ -286,35 +270,42 @@ static void finalize_coding_system (void *header, int for_disksave); #ifdef MULE static const struct lrecord_description ccs_description_1[] = { - { XD_LISP_OBJECT, offsetof(charset_conversion_spec, from_charset), 2 }, + { XD_LISP_OBJECT, offsetof (charset_conversion_spec, from_charset) }, + { XD_LISP_OBJECT, offsetof (charset_conversion_spec, to_charset) }, { XD_END } }; static const struct struct_description ccs_description = { - sizeof(charset_conversion_spec), + sizeof (charset_conversion_spec), ccs_description_1 }; - + static const struct lrecord_description ccsd_description_1[] = { - XD_DYNARR_DESC(charset_conversion_spec_dynarr, &ccs_description), + XD_DYNARR_DESC (charset_conversion_spec_dynarr, &ccs_description), { XD_END } }; static const struct struct_description ccsd_description = { - sizeof(charset_conversion_spec_dynarr), + sizeof (charset_conversion_spec_dynarr), ccsd_description_1 }; #endif static const struct lrecord_description coding_system_description[] = { - { XD_LISP_OBJECT, offsetof(struct Lisp_Coding_System, name), 2 }, - { XD_LISP_OBJECT, offsetof(struct Lisp_Coding_System, mnemonic), 3 }, - { XD_LISP_OBJECT, offsetof(struct Lisp_Coding_System, eol_lf), 3 }, + { XD_LISP_OBJECT, offsetof (Lisp_Coding_System, name) }, + { XD_LISP_OBJECT, offsetof (Lisp_Coding_System, doc_string) }, + { XD_LISP_OBJECT, offsetof (Lisp_Coding_System, mnemonic) }, + { XD_LISP_OBJECT, offsetof (Lisp_Coding_System, post_read_conversion) }, + { XD_LISP_OBJECT, offsetof (Lisp_Coding_System, pre_write_conversion) }, + { XD_LISP_OBJECT, offsetof (Lisp_Coding_System, eol_lf) }, + { XD_LISP_OBJECT, offsetof (Lisp_Coding_System, eol_crlf) }, + { XD_LISP_OBJECT, offsetof (Lisp_Coding_System, eol_cr) }, #ifdef MULE - { XD_LISP_OBJECT, offsetof(struct Lisp_Coding_System, iso2022.initial_charset), 4 }, - { XD_STRUCT_PTR, offsetof(struct Lisp_Coding_System, iso2022.input_conv), 1, &ccsd_description }, - { XD_STRUCT_PTR, offsetof(struct Lisp_Coding_System, iso2022.output_conv), 1, &ccsd_description }, - { XD_LISP_OBJECT, offsetof(struct Lisp_Coding_System, ccl.decode), 2 }, + { XD_LISP_OBJECT_ARRAY, offsetof (Lisp_Coding_System, iso2022.initial_charset), 4 }, + { XD_STRUCT_PTR, offsetof (Lisp_Coding_System, iso2022.input_conv), 1, &ccsd_description }, + { XD_STRUCT_PTR, offsetof (Lisp_Coding_System, iso2022.output_conv), 1, &ccsd_description }, + { XD_LISP_OBJECT, offsetof (Lisp_Coding_System, ccl.decode) }, + { XD_LISP_OBJECT, offsetof (Lisp_Coding_System, ccl.encode) }, #endif { XD_END } }; @@ -323,7 +314,7 @@ DEFINE_LRECORD_IMPLEMENTATION ("coding-system", coding_system, mark_coding_system, print_coding_system, finalize_coding_system, 0, 0, coding_system_description, - struct Lisp_Coding_System); + Lisp_Coding_System); static Lisp_Object mark_coding_system (Lisp_Object obj) @@ -424,7 +415,7 @@ finalize_coding_system (void *header, int for_disksave) } } -static enum eol_type +static eol_type_t symbol_to_eol_type (Lisp_Object symbol) { CHECK_SYMBOL (symbol); @@ -438,7 +429,7 @@ symbol_to_eol_type (Lisp_Object symbol) } static Lisp_Object -eol_type_to_symbol (enum eol_type type) +eol_type_to_symbol (eol_type_t type) { switch (type) { @@ -529,15 +520,21 @@ associated coding system object is returned. */ (coding_system_or_name)) { - if (CODING_SYSTEMP (coding_system_or_name)) - return coding_system_or_name; - if (NILP (coding_system_or_name)) coding_system_or_name = Qbinary; + else if (CODING_SYSTEMP (coding_system_or_name)) + return coding_system_or_name; else CHECK_SYMBOL (coding_system_or_name); - return Fgethash (coding_system_or_name, Vcoding_system_hash_table, Qnil); + while (1) + { + coding_system_or_name = + Fgethash (coding_system_or_name, Vcoding_system_hash_table, Qnil); + + if (CODING_SYSTEMP (coding_system_or_name) || NILP (coding_system_or_name)) + return coding_system_or_name; + } } DEFUN ("get-coding-system", Fget_coding_system, 1, 1, 0, /* @@ -571,8 +568,7 @@ add_coding_system_to_list_mapper (Lisp_Object key, Lisp_Object value, (struct coding_system_list_closure *) coding_system_list_closure; Lisp_Object *coding_system_list = cscl->coding_system_list; - *coding_system_list = Fcons (XCODING_SYSTEM (value)->name, - *coding_system_list); + *coding_system_list = Fcons (key, *coding_system_list); return 0; } @@ -715,7 +711,7 @@ nil or 'undecided JIS (the Japanese encoding commonly used for e-mail), EUC (the standard Unix encoding for Japanese and other languages), and Compound Text (the encoding used in X11). You can specify more - specific information about the conversion with the FLAGS argument. + specific information about the conversion with the PROPS argument. 'big5 Big5 (the encoding commonly used for Taiwanese). 'ccl @@ -772,12 +768,12 @@ character set. Recognized properties are: 'post-read-conversion Function called after a file has been read in, to perform the - decoding. Called with two arguments, BEG and END, denoting + decoding. Called with two arguments, START and END, denoting a region of the current buffer to be decoded. 'pre-write-conversion Function called before a file is written out, to perform the - encoding. Called with two arguments, BEG and END, denoting + encoding. Called with two arguments, START and END, denoting a region of the current buffer to be encoded. @@ -865,7 +861,6 @@ if TYPE is 'ccl: (name, type, doc_string, props)) { Lisp_Coding_System *codesys; - Lisp_Object rest, key, value; enum coding_system_type ty; int need_to_setup_eol_systems = 1; @@ -897,92 +892,118 @@ if TYPE is 'ccl: CHECK_STRING (doc_string); CODING_SYSTEM_DOC_STRING (codesys) = doc_string; - EXTERNAL_PROPERTY_LIST_LOOP (rest, key, value, props) - { - if (EQ (key, Qmnemonic)) - { - if (!NILP (value)) - CHECK_STRING (value); - CODING_SYSTEM_MNEMONIC (codesys) = value; - } + { + EXTERNAL_PROPERTY_LIST_LOOP_3 (key, value, props) + { + if (EQ (key, Qmnemonic)) + { + if (!NILP (value)) + CHECK_STRING (value); + CODING_SYSTEM_MNEMONIC (codesys) = value; + } - else if (EQ (key, Qeol_type)) - { - need_to_setup_eol_systems = NILP (value); - if (EQ (value, Qt)) - value = Qnil; - CODING_SYSTEM_EOL_TYPE (codesys) = symbol_to_eol_type (value); - } + else if (EQ (key, Qeol_type)) + { + need_to_setup_eol_systems = NILP (value); + if (EQ (value, Qt)) + value = Qnil; + CODING_SYSTEM_EOL_TYPE (codesys) = symbol_to_eol_type (value); + } - else if (EQ (key, Qpost_read_conversion)) CODING_SYSTEM_POST_READ_CONVERSION (codesys) = value; - else if (EQ (key, Qpre_write_conversion)) CODING_SYSTEM_PRE_WRITE_CONVERSION (codesys) = value; + else if (EQ (key, Qpost_read_conversion)) CODING_SYSTEM_POST_READ_CONVERSION (codesys) = value; + else if (EQ (key, Qpre_write_conversion)) CODING_SYSTEM_PRE_WRITE_CONVERSION (codesys) = value; #ifdef MULE - else if (ty == CODESYS_ISO2022) - { + else if (ty == CODESYS_ISO2022) + { #define FROB_INITIAL_CHARSET(charset_num) \ CODING_SYSTEM_ISO2022_INITIAL_CHARSET (codesys, charset_num) = \ ((EQ (value, Qt) || EQ (value, Qnil)) ? value : Fget_charset (value)) - if (EQ (key, Qcharset_g0)) FROB_INITIAL_CHARSET (0); - else if (EQ (key, Qcharset_g1)) FROB_INITIAL_CHARSET (1); - else if (EQ (key, Qcharset_g2)) FROB_INITIAL_CHARSET (2); - else if (EQ (key, Qcharset_g3)) FROB_INITIAL_CHARSET (3); + if (EQ (key, Qcharset_g0)) FROB_INITIAL_CHARSET (0); + else if (EQ (key, Qcharset_g1)) FROB_INITIAL_CHARSET (1); + else if (EQ (key, Qcharset_g2)) FROB_INITIAL_CHARSET (2); + else if (EQ (key, Qcharset_g3)) FROB_INITIAL_CHARSET (3); #define FROB_FORCE_CHARSET(charset_num) \ CODING_SYSTEM_ISO2022_FORCE_CHARSET_ON_OUTPUT (codesys, charset_num) = !NILP (value) - else if (EQ (key, Qforce_g0_on_output)) FROB_FORCE_CHARSET (0); - else if (EQ (key, Qforce_g1_on_output)) FROB_FORCE_CHARSET (1); - else if (EQ (key, Qforce_g2_on_output)) FROB_FORCE_CHARSET (2); - else if (EQ (key, Qforce_g3_on_output)) FROB_FORCE_CHARSET (3); + else if (EQ (key, Qforce_g0_on_output)) FROB_FORCE_CHARSET (0); + else if (EQ (key, Qforce_g1_on_output)) FROB_FORCE_CHARSET (1); + else if (EQ (key, Qforce_g2_on_output)) FROB_FORCE_CHARSET (2); + else if (EQ (key, Qforce_g3_on_output)) FROB_FORCE_CHARSET (3); #define FROB_BOOLEAN_PROPERTY(prop) \ CODING_SYSTEM_ISO2022_##prop (codesys) = !NILP (value) - else if (EQ (key, Qshort)) FROB_BOOLEAN_PROPERTY (SHORT); - else if (EQ (key, Qno_ascii_eol)) FROB_BOOLEAN_PROPERTY (NO_ASCII_EOL); - else if (EQ (key, Qno_ascii_cntl)) FROB_BOOLEAN_PROPERTY (NO_ASCII_CNTL); - else if (EQ (key, Qseven)) FROB_BOOLEAN_PROPERTY (SEVEN); - else if (EQ (key, Qlock_shift)) FROB_BOOLEAN_PROPERTY (LOCK_SHIFT); - else if (EQ (key, Qno_iso6429)) FROB_BOOLEAN_PROPERTY (NO_ISO6429); - else if (EQ (key, Qescape_quoted)) FROB_BOOLEAN_PROPERTY (ESCAPE_QUOTED); + else if (EQ (key, Qshort)) FROB_BOOLEAN_PROPERTY (SHORT); + else if (EQ (key, Qno_ascii_eol)) FROB_BOOLEAN_PROPERTY (NO_ASCII_EOL); + else if (EQ (key, Qno_ascii_cntl)) FROB_BOOLEAN_PROPERTY (NO_ASCII_CNTL); + else if (EQ (key, Qseven)) FROB_BOOLEAN_PROPERTY (SEVEN); + else if (EQ (key, Qlock_shift)) FROB_BOOLEAN_PROPERTY (LOCK_SHIFT); + else if (EQ (key, Qno_iso6429)) FROB_BOOLEAN_PROPERTY (NO_ISO6429); + else if (EQ (key, Qescape_quoted)) FROB_BOOLEAN_PROPERTY (ESCAPE_QUOTED); + + else if (EQ (key, Qinput_charset_conversion)) + { + codesys->iso2022.input_conv = + Dynarr_new (charset_conversion_spec); + parse_charset_conversion_specs (codesys->iso2022.input_conv, + value); + } + else if (EQ (key, Qoutput_charset_conversion)) + { + codesys->iso2022.output_conv = + Dynarr_new (charset_conversion_spec); + parse_charset_conversion_specs (codesys->iso2022.output_conv, + value); + } + else + signal_simple_error ("Unrecognized property", key); + } + else if (EQ (type, Qccl)) + { + Lisp_Object sym; + struct ccl_program test_ccl; + Extbyte *suffix; + + /* Check key first. */ + if (EQ (key, Qdecode)) + suffix = "-ccl-decode"; + else if (EQ (key, Qencode)) + suffix = "-ccl-encode"; + else + signal_simple_error ("Unrecognized property", key); + + /* If value is vector, register it as a ccl program + associated with an newly created symbol for + backward compatibility. */ + if (VECTORP (value)) + { + sym = Fintern (concat2 (Fsymbol_name (name), + build_string (suffix)), + Qnil); + Fregister_ccl_program (sym, value); + } + else + { + CHECK_SYMBOL (value); + sym = value; + } + /* check if the given ccl programs are valid. */ + if (setup_ccl_program (&test_ccl, sym) < 0) + signal_simple_error ("Invalid CCL program", value); + + if (EQ (key, Qdecode)) + CODING_SYSTEM_CCL_DECODE (codesys) = sym; + else if (EQ (key, Qencode)) + CODING_SYSTEM_CCL_ENCODE (codesys) = sym; - else if (EQ (key, Qinput_charset_conversion)) - { - codesys->iso2022.input_conv = - Dynarr_new (charset_conversion_spec); - parse_charset_conversion_specs (codesys->iso2022.input_conv, - value); - } - else if (EQ (key, Qoutput_charset_conversion)) - { - codesys->iso2022.output_conv = - Dynarr_new (charset_conversion_spec); - parse_charset_conversion_specs (codesys->iso2022.output_conv, - value); - } - else - signal_simple_error ("Unrecognized property", key); - } - else if (EQ (type, Qccl)) - { - if (EQ (key, Qdecode)) - { - CHECK_VECTOR (value); - CODING_SYSTEM_CCL_DECODE (codesys) = value; - } - else if (EQ (key, Qencode)) - { - CHECK_VECTOR (value); - CODING_SYSTEM_CCL_ENCODE (codesys) = value; - } - else - signal_simple_error ("Unrecognized property", key); - } + } #endif /* MULE */ - else - signal_simple_error ("Unrecognized property", key); - } + else + signal_simple_error ("Unrecognized property", key); + } + } if (need_to_setup_eol_systems) setup_eol_coding_systems (codesys); @@ -1025,42 +1046,169 @@ be created. return new_coding_system; } +DEFUN ("coding-system-canonical-name-p", Fcoding_system_canonical_name_p, 1, 1, 0, /* +Return t if OBJECT names a coding system, and is not a coding system alias. +*/ + (object)) +{ + return CODING_SYSTEMP (Fgethash (object, Vcoding_system_hash_table, Qnil)) + ? Qt : Qnil; +} + +DEFUN ("coding-system-alias-p", Fcoding_system_alias_p, 1, 1, 0, /* +Return t if OBJECT is a coding system alias. +All coding system aliases are created by `define-coding-system-alias'. +*/ + (object)) +{ + return SYMBOLP (Fgethash (object, Vcoding_system_hash_table, Qzero)) + ? Qt : Qnil; +} + +DEFUN ("coding-system-aliasee", Fcoding_system_aliasee, 1, 1, 0, /* +Return the coding-system symbol for which symbol ALIAS is an alias. +*/ + (alias)) +{ + Lisp_Object aliasee = Fgethash (alias, Vcoding_system_hash_table, Qnil); + if (SYMBOLP (aliasee)) + return aliasee; + else + signal_simple_error ("Symbol is not a coding system alias", alias); + return Qnil; /* To keep the compiler happy */ +} + +static Lisp_Object +append_suffix_to_symbol (Lisp_Object symbol, const char *ascii_string) +{ + return Fintern (concat2 (Fsymbol_name (symbol), build_string (ascii_string)), + Qnil); +} + +/* A maphash function, for removing dangling coding system aliases. */ +static int +dangling_coding_system_alias_p (Lisp_Object alias, + Lisp_Object aliasee, + void *dangling_aliases) +{ + if (SYMBOLP (aliasee) + && NILP (Fgethash (aliasee, Vcoding_system_hash_table, Qnil))) + { + (*(int *) dangling_aliases)++; + return 1; + } + else + return 0; +} + DEFUN ("define-coding-system-alias", Fdefine_coding_system_alias, 2, 2, 0, /* -Define symbol ALIAS as an alias for coding system CODING-SYSTEM. +Define symbol ALIAS as an alias for coding system ALIASEE. + +You can use this function to redefine an alias that has already been defined, +but you cannot redefine a name which is the canonical name for a coding system. +\(a canonical name of a coding system is what is returned when you call +`coding-system-name' on a coding system). + +ALIASEE itself can be an alias, which allows you to define nested aliases. + +You are forbidden, however, from creating alias loops or `dangling' aliases. +These will be detected, and an error will be signaled if you attempt to do so. + +If ALIASEE is nil, then ALIAS will simply be undefined. + +See also `coding-system-alias-p', `coding-system-aliasee', +and `coding-system-canonical-name-p'. */ - (alias, coding_system)) + (alias, aliasee)) { + Lisp_Object real_coding_system, probe; + CHECK_SYMBOL (alias); - if (!NILP (Ffind_coding_system (alias))) - signal_simple_error ("Symbol already names a coding system", alias); - coding_system = Fget_coding_system (coding_system); - Fputhash (alias, coding_system, Vcoding_system_hash_table); - /* Set up aliases for subsidiaries. */ - if (XCODING_SYSTEM_EOL_TYPE (coding_system) == EOL_AUTODETECT) + if (!NILP (Fcoding_system_canonical_name_p (alias))) + signal_simple_error + ("Symbol is the canonical name of a coding system and cannot be redefined", + alias); + + if (NILP (aliasee)) { - Lisp_Object str; - XSETSTRING (str, symbol_name (XSYMBOL (alias))); -#define FROB(type, name) \ - do { \ - Lisp_Object subsidiary = XCODING_SYSTEM_EOL_##type (coding_system); \ - if (!NILP (subsidiary)) \ - Fdefine_coding_system_alias \ - (Fintern (concat2 (str, build_string (name)), Qnil), subsidiary); \ - } while (0) - FROB (LF, "-unix"); - FROB (CRLF, "-dos"); - FROB (CR, "-mac"); -#undef FROB + Lisp_Object subsidiary_unix = append_suffix_to_symbol (alias, "-unix"); + Lisp_Object subsidiary_dos = append_suffix_to_symbol (alias, "-dos"); + Lisp_Object subsidiary_mac = append_suffix_to_symbol (alias, "-mac"); + + Fremhash (alias, Vcoding_system_hash_table); + + /* Undefine subsidiary aliases, + presumably created by a previous call to this function */ + if (! NILP (Fcoding_system_alias_p (subsidiary_unix)) && + ! NILP (Fcoding_system_alias_p (subsidiary_dos)) && + ! NILP (Fcoding_system_alias_p (subsidiary_mac))) + { + Fdefine_coding_system_alias (subsidiary_unix, Qnil); + Fdefine_coding_system_alias (subsidiary_dos, Qnil); + Fdefine_coding_system_alias (subsidiary_mac, Qnil); + } + + /* Undefine dangling coding system aliases. */ + { + int dangling_aliases; + + do { + dangling_aliases = 0; + elisp_map_remhash (dangling_coding_system_alias_p, + Vcoding_system_hash_table, + &dangling_aliases); + } while (dangling_aliases > 0); + } + + return Qnil; + } + + if (CODING_SYSTEMP (aliasee)) + aliasee = XCODING_SYSTEM_NAME (aliasee); + + /* Checks that aliasee names a coding-system */ + real_coding_system = Fget_coding_system (aliasee); + + /* Check for coding system alias loops */ + if (EQ (alias, aliasee)) + alias_loop: signal_simple_error_2 + ("Attempt to create a coding system alias loop", alias, aliasee); + + for (probe = aliasee; + SYMBOLP (probe); + probe = Fgethash (probe, Vcoding_system_hash_table, Qzero)) + { + if (EQ (probe, alias)) + goto alias_loop; } - /* FSF return value is a vector of [ALIAS-unix ALIAS-doc ALIAS-mac], + + Fputhash (alias, aliasee, Vcoding_system_hash_table); + + /* Set up aliases for subsidiaries. + #### There must be a better way to handle subsidiary coding systems. */ + { + static const char *suffixes[] = { "-unix", "-dos", "-mac" }; + int i; + for (i = 0; i < countof (suffixes); i++) + { + Lisp_Object alias_subsidiary = + append_suffix_to_symbol (alias, suffixes[i]); + Lisp_Object aliasee_subsidiary = + append_suffix_to_symbol (aliasee, suffixes[i]); + + if (! NILP (Ffind_coding_system (aliasee_subsidiary))) + Fdefine_coding_system_alias (alias_subsidiary, aliasee_subsidiary); + } + } + /* FSF return value is a vector of [ALIAS-unix ALIAS-dos ALIAS-mac], but it doesn't look intentional, so I'd rather return something meaningful or nothing at all. */ return Qnil; } static Lisp_Object -subsidiary_coding_system (Lisp_Object coding_system, enum eol_type type) +subsidiary_coding_system (Lisp_Object coding_system, eol_type_t type) { Lisp_Coding_System *cs = XCODING_SYSTEM (coding_system); Lisp_Object new_coding_system; @@ -1074,7 +1222,7 @@ subsidiary_coding_system (Lisp_Object coding_system, enum eol_type type) case EOL_LF: new_coding_system = CODING_SYSTEM_EOL_LF (cs); break; case EOL_CR: new_coding_system = CODING_SYSTEM_EOL_CR (cs); break; case EOL_CRLF: new_coding_system = CODING_SYSTEM_EOL_CRLF (cs); break; - default: abort (); + default: abort (); return Qnil; } return NILP (new_coding_system) ? coding_system : new_coding_system; @@ -1285,7 +1433,7 @@ decode_coding_category (Lisp_Object symbol) int i; CHECK_SYMBOL (symbol); - for (i = 0; i <= CODING_CATEGORY_LAST; i++) + for (i = 0; i < CODING_CATEGORY_LAST; i++) if (EQ (coding_category_symbol[i], symbol)) return i; @@ -1301,7 +1449,7 @@ Return a list of all recognized coding categories. int i; Lisp_Object list = Qnil; - for (i = CODING_CATEGORY_LAST; i >= 0; i--) + for (i = CODING_CATEGORY_LAST - 1; i >= 0; i--) list = Fcons (coding_category_symbol[i], list); return list; } @@ -1315,13 +1463,13 @@ previously. */ (list)) { - int category_to_priority[CODING_CATEGORY_LAST + 1]; + int category_to_priority[CODING_CATEGORY_LAST]; int i, j; Lisp_Object rest; /* First generate a list that maps coding categories to priorities. */ - for (i = 0; i <= CODING_CATEGORY_LAST; i++) + for (i = 0; i < CODING_CATEGORY_LAST; i++) category_to_priority[i] = -1; /* Highest priority comes from the specified list. */ @@ -1338,7 +1486,7 @@ previously. /* Now go through the existing categories by priority to retrieve the categories not yet specified and preserve their priority order. */ - for (j = 0; j <= CODING_CATEGORY_LAST; j++) + for (j = 0; j < CODING_CATEGORY_LAST; j++) { int cat = fcd->coding_category_by_priority[j]; if (category_to_priority[cat] < 0) @@ -1348,7 +1496,7 @@ previously. /* Now we need to construct the inverse of the mapping we just constructed. */ - for (i = 0; i <= CODING_CATEGORY_LAST; i++) + for (i = 0; i < CODING_CATEGORY_LAST; i++) fcd->coding_category_by_priority[category_to_priority[i]] = i; /* Phew! That was confusing. */ @@ -1363,7 +1511,7 @@ Return a list of coding categories in descending order of priority. int i; Lisp_Object list = Qnil; - for (i = CODING_CATEGORY_LAST; i >= 0; i--) + for (i = CODING_CATEGORY_LAST - 1; i >= 0; i--) list = Fcons (coding_category_symbol[fcd->coding_category_by_priority[i]], list); return list; @@ -1401,7 +1549,7 @@ Return the coding system associated with a coding category. struct detection_state { - enum eol_type eol_type; + eol_type_t eol_type; int seen_non_ascii; int mask; #ifdef MULE @@ -1482,30 +1630,26 @@ mask_has_at_most_one_bit_p (int mask) return (mask & (mask - 1)) == 0; } -static enum eol_type -detect_eol_type (struct detection_state *st, CONST unsigned char *src, - unsigned int n) +static eol_type_t +detect_eol_type (struct detection_state *st, const Extbyte *src, + Lstream_data_count n) { - int c; - while (n--) { - c = *src++; - if (c == '\r') - st->eol.just_saw_cr = 1; - else + unsigned char c = *(unsigned char *)src++; + if (c == '\n') { - if (c == '\n') - { - if (st->eol.just_saw_cr) - return EOL_CRLF; - else if (st->eol.seen_anything) - return EOL_LF; - } - else if (st->eol.just_saw_cr) - return EOL_CR; - st->eol.just_saw_cr = 0; + if (st->eol.just_saw_cr) + return EOL_CRLF; + else if (st->eol.seen_anything) + return EOL_LF; } + else if (st->eol.just_saw_cr) + return EOL_CR; + else if (c == '\r') + st->eol.just_saw_cr = 1; + else + st->eol.just_saw_cr = 0; st->eol.seen_anything = 1; } @@ -1530,11 +1674,9 @@ detect_eol_type (struct detection_state *st, CONST unsigned char *src, */ static int -detect_coding_type (struct detection_state *st, CONST unsigned char *src, - unsigned int n, int just_do_eol) +detect_coding_type (struct detection_state *st, const Extbyte *src, + Lstream_data_count n, int just_do_eol) { - int c; - if (st->eol_type == EOL_AUTODETECT) st->eol_type = detect_eol_type (st, src, n); @@ -1545,7 +1687,7 @@ detect_coding_type (struct detection_state *st, CONST unsigned char *src, { for (; n; n--, src++) { - c = *src; + unsigned char c = *(unsigned char *) src; if ((c < 0x20 && !acceptable_control_char_p (c)) || c >= 0x80) { st->seen_non_ascii = 1; @@ -1619,7 +1761,7 @@ coding_system_from_mask (int mask) #endif /* Look through the coding categories by priority and find the first one that is allowed. */ - for (i = 0; i <= CODING_CATEGORY_LAST; i++) + for (i = 0; i < CODING_CATEGORY_LAST; i++) { cat = fcd->coding_category_by_priority[i]; if ((mask & (1 << cat)) && @@ -1635,16 +1777,20 @@ coding_system_from_mask (int mask) /* Given a seekable read stream and potential coding system and EOL type as specified, do any autodetection that is called for. If the - coding system and/or EOL type are not autodetect, they will be left + coding system and/or EOL type are not `autodetect', they will be left alone; but this function will never return an autodetect coding system or EOL type. This function does not automatically fetch subsidiary coding systems; that should be unnecessary with the explicit eol-type argument. */ +#define LENGTH(string_constant) (sizeof (string_constant) - 1) +/* number of leading lines to check for a coding cookie */ +#define LINES_TO_CHECK 2 + void determine_real_coding_system (Lstream *stream, Lisp_Object *codesys_in_out, - enum eol_type *eol_type_in_out) + eol_type_t *eol_type_in_out) { struct detection_state decst; @@ -1656,68 +1802,125 @@ determine_real_coding_system (Lstream *stream, Lisp_Object *codesys_in_out, decst.mask = ~0; /* If autodetection is called for, do it now. */ - if (XCODING_SYSTEM_TYPE (*codesys_in_out) == CODESYS_AUTODETECT || - *eol_type_in_out == EOL_AUTODETECT) + if (XCODING_SYSTEM_TYPE (*codesys_in_out) == CODESYS_AUTODETECT + || *eol_type_in_out == EOL_AUTODETECT) { - unsigned char random_buffer[4096]; - int nread; + Extbyte buf[4096]; Lisp_Object coding_system = Qnil; - - nread = Lstream_read (stream, random_buffer, sizeof (random_buffer)); - if (nread) - { - unsigned char *cp = random_buffer; - - while (cp < random_buffer + nread) - { - if ((*cp++ == 'c') && (cp < random_buffer + nread) && - (*cp++ == 'o') && (cp < random_buffer + nread) && - (*cp++ == 'd') && (cp < random_buffer + nread) && - (*cp++ == 'i') && (cp < random_buffer + nread) && - (*cp++ == 'n') && (cp < random_buffer + nread) && - (*cp++ == 'g') && (cp < random_buffer + nread) && - (*cp++ == ':') && (cp < random_buffer + nread)) + Extbyte *p; + Lstream_data_count nread = Lstream_read (stream, buf, sizeof (buf)); + Extbyte *scan_end; + int lines_checked = 0; + + /* Look for initial "-*-"; mode line prefix */ + for (p = buf, + scan_end = buf + nread - LENGTH ("-*-coding:?-*-"); + p <= scan_end + && lines_checked < LINES_TO_CHECK; + p++) + if (*p == '-' && *(p+1) == '*' && *(p+2) == '-') + { + Extbyte *local_vars_beg = p + 3; + /* Look for final "-*-"; mode line suffix */ + for (p = local_vars_beg, + scan_end = buf + nread - LENGTH ("-*-"); + p <= scan_end + && lines_checked < LINES_TO_CHECK; + p++) + if (*p == '-' && *(p+1) == '*' && *(p+2) == '-') { - unsigned char coding_system_name[4096 - 6]; - unsigned char *np = coding_system_name; - - while ( (cp < random_buffer + nread) - && ((*cp == ' ') || (*cp == '\t')) ) - { - cp++; - } - while ( (cp < random_buffer + nread) && - (*cp != ' ') && (*cp != '\t') && (*cp != ';') ) - { - *np++ = *cp++; - } - *np = 0; - coding_system - = Ffind_coding_system (intern ((char *) coding_system_name)); + Extbyte *suffix = p; + /* Look for "coding:" */ + for (p = local_vars_beg, + scan_end = suffix - LENGTH ("coding:?"); + p <= scan_end; + p++) + if (memcmp ("coding:", p, LENGTH ("coding:")) == 0 + && (p == local_vars_beg + || (*(p-1) == ' ' || + *(p-1) == '\t' || + *(p-1) == ';'))) + { + Extbyte save; + int n; + p += LENGTH ("coding:"); + while (*p == ' ' || *p == '\t') p++; + + /* Get coding system name */ + save = *suffix; *suffix = '\0'; + /* Characters valid in a MIME charset name (rfc 1521), + and in a Lisp symbol name. */ + n = strspn ( (char *) p, + "ABCDEFGHIJKLMNOPQRSTUVWXYZ" + "abcdefghijklmnopqrstuvwxyz" + "0123456789" + "!$%&*+-.^_{|}~"); + *suffix = save; + if (n > 0) + { + save = p[n]; p[n] = '\0'; + coding_system = + Ffind_coding_system (intern ((char *) p)); + p[n] = save; + } + break; + } break; } - } - if (EQ(coding_system, Qnil)) - do{ - if (detect_coding_type (&decst, random_buffer, nread, - XCODING_SYSTEM_TYPE (*codesys_in_out) - != CODESYS_AUTODETECT)) - break; - nread = Lstream_read (stream, - random_buffer, sizeof (random_buffer)); - if (!nread) - break; - } while(1); - } + /* #### file must use standard EOLs or we miss 2d line */ + /* #### not to mention this is broken for UTF-16 DOS files */ + else if (*p == '\n' || *p == '\r') + { + lines_checked++; + /* skip past multibyte (DOS) newline */ + if (*p == '\r' && *(p+1) == '\n') p++; + } + break; + } + /* #### file must use standard EOLs or we miss 2d line */ + /* #### not to mention this is broken for UTF-16 DOS files */ + else if (*p == '\n' || *p == '\r') + { + lines_checked++; + /* skip past multibyte (DOS) newline */ + if (*p == '\r' && *(p+1) == '\n') p++; + } + + if (NILP (coding_system)) + do + { + if (detect_coding_type (&decst, buf, nread, + XCODING_SYSTEM_TYPE (*codesys_in_out) + != CODESYS_AUTODETECT)) + break; + nread = Lstream_read (stream, buf, sizeof (buf)); + if (nread == 0) + break; + } + while (1); + + else if (XCODING_SYSTEM_TYPE (*codesys_in_out) == CODESYS_AUTODETECT + && XCODING_SYSTEM_EOL_TYPE (coding_system) == EOL_AUTODETECT) + do + { + if (detect_coding_type (&decst, buf, nread, 1)) + break; + nread = Lstream_read (stream, buf, sizeof (buf)); + if (!nread) + break; + } + while (1); + *eol_type_in_out = decst.eol_type; if (XCODING_SYSTEM_TYPE (*codesys_in_out) == CODESYS_AUTODETECT) { - if (EQ(coding_system, Qnil)) + if (NILP (coding_system)) *codesys_in_out = coding_system_from_mask (decst.mask); else *codesys_in_out = coding_system; } } + /* If we absolutely can't determine the EOL type, just assume LF. */ if (*eol_type_in_out == EOL_AUTODETECT) *eol_type_in_out = EOL_LF; @@ -1727,8 +1930,8 @@ determine_real_coding_system (Lstream *stream, Lisp_Object *codesys_in_out, DEFUN ("detect-coding-region", Fdetect_coding_region, 2, 3, 0, /* Detect coding system of the text in the region between START and END. -Returned a list of possible coding systems ordered by priority. -If only ASCII characters are found, it returns 'undecided or one of +Return a list of possible coding systems ordered by priority. +If only ASCII characters are found, return 'undecided or one of its subsidiary coding systems according to a detected end-of-line type. Optional arg BUFFER defaults to the current buffer. */ @@ -1753,8 +1956,8 @@ type. Optional arg BUFFER defaults to the current buffer. decst.mask = ~0; while (1) { - unsigned char random_buffer[4096]; - int nread = Lstream_read (istr, random_buffer, sizeof (random_buffer)); + Extbyte random_buffer[4096]; + Lstream_data_count nread = Lstream_read (istr, random_buffer, sizeof (random_buffer)); if (!nread) break; @@ -1773,7 +1976,7 @@ type. Optional arg BUFFER defaults to the current buffer. #ifdef MULE decst.mask = postprocess_iso2022_mask (decst.mask); #endif - for (i = CODING_CATEGORY_LAST; i >= 0; i--) + for (i = CODING_CATEGORY_LAST - 1; i >= 0; i--) { int sys = fcd->coding_category_by_priority[i]; if (decst.mask & (1 << sys)) @@ -1905,7 +2108,7 @@ struct decoding_stream EOL type stored in CODESYS because the latter might indicate automatic EOL-type detection while the former will always indicate a particular EOL type. */ - enum eol_type eol_type; + eol_type_t eol_type; #ifdef MULE /* Additional ISO2022 information. We define the structure above because it's also needed by the detection routines. */ @@ -1921,8 +2124,10 @@ struct decoding_stream struct detection_state decst; }; -static int decoding_reader (Lstream *stream, unsigned char *data, size_t size); -static int decoding_writer (Lstream *stream, CONST unsigned char *data, size_t size); +static Lstream_data_count decoding_reader (Lstream *stream, + unsigned char *data, Lstream_data_count size); +static Lstream_data_count decoding_writer (Lstream *stream, + const unsigned char *data, Lstream_data_count size); static int decoding_rewinder (Lstream *stream); static int decoding_seekable_p (Lstream *stream); static int decoding_flusher (Lstream *stream); @@ -1954,12 +2159,12 @@ decoding_marker (Lisp_Object stream) /* Read SIZE bytes of data and store it into DATA. We are a decoding stream so we read data from the other end, decode it, and store it into DATA. */ -static int -decoding_reader (Lstream *stream, unsigned char *data, size_t size) +static Lstream_data_count +decoding_reader (Lstream *stream, unsigned char *data, Lstream_data_count size) { struct decoding_stream *str = DECODING_STREAM_DATA (stream); unsigned char *orig_data = data; - int read_size; + Lstream_data_count read_size; int error_occurred = 0; /* We need to interface to mule_decode(), which expects to take some @@ -1975,7 +2180,7 @@ decoding_reader (Lstream *stream, unsigned char *data, size_t size) most SIZE bytes, and delete the data from the runoff. */ if (Dynarr_length (str->runoff) > 0) { - size_t chunk = min (size, (size_t) Dynarr_length (str->runoff)); + Lstream_data_count chunk = min (size, (Lstream_data_count) Dynarr_length (str->runoff)); memcpy (data, Dynarr_atp (str->runoff, 0), chunk); Dynarr_delete_many (str->runoff, 0, chunk); data += chunk; @@ -2007,7 +2212,7 @@ decoding_reader (Lstream *stream, unsigned char *data, size_t size) /* There might be some more end data produced in the translation. See the comment above. */ str->flags |= CODING_STATE_END; - mule_decode (stream, data, str->runoff, read_size); + mule_decode (stream, (Extbyte *) data, str->runoff, read_size); } if (data - orig_data == 0) @@ -2016,16 +2221,16 @@ decoding_reader (Lstream *stream, unsigned char *data, size_t size) return data - orig_data; } -static int -decoding_writer (Lstream *stream, CONST unsigned char *data, size_t size) +static Lstream_data_count +decoding_writer (Lstream *stream, const unsigned char *data, Lstream_data_count size) { struct decoding_stream *str = DECODING_STREAM_DATA (stream); - int retval; + Lstream_data_count retval; /* Decode all our data into the runoff, and then attempt to write it all out to the other end. Remove whatever chunk we succeeded in writing. */ - mule_decode (stream, data, str->runoff, size); + mule_decode (stream, (Extbyte *) data, str->runoff, size); retval = Lstream_write (str->other_end, Dynarr_atp (str->runoff, 0), Dynarr_length (str->runoff)); if (retval > 0) @@ -2052,6 +2257,13 @@ reset_decoding_stream (struct decoding_stream *str) } str->counter = 0; #endif /* MULE */ + if (CODING_SYSTEM_TYPE (str->codesys) == CODESYS_AUTODETECT + || CODING_SYSTEM_EOL_TYPE (str->codesys) == EOL_AUTODETECT) + { + xzero (str->decst); + str->decst.eol_type = EOL_AUTODETECT; + str->decst.mask = ~0; + } str->flags = str->ch = 0; } @@ -2127,7 +2339,7 @@ set_decoding_stream_coding_system (Lstream *lstr, Lisp_Object codesys) static Lisp_Object make_decoding_stream_1 (Lstream *stream, Lisp_Object codesys, - CONST char *mode) + const char *mode) { Lstream *lstr = Lstream_new (lstream_decoding, mode); struct decoding_stream *str = DECODING_STREAM_DATA (lstr); @@ -2170,8 +2382,8 @@ make_decoding_output_stream (Lstream *stream, Lisp_Object codesys) be used for both reading and writing. */ static void -mule_decode (Lstream *decoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +mule_decode (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { struct decoding_stream *str = DECODING_STREAM_DATA (decoding); @@ -2235,7 +2447,10 @@ mule_decode (Lstream *decoding, CONST unsigned char *src, break; case CODESYS_CCL: str->ccl.last_block = str->flags & CODING_STATE_END; - ccl_driver (&str->ccl, src, dst, n, 0, CCL_MODE_DECODING); + /* When applying ccl program to stream, MUST NOT set NULL + pointer to src. */ + ccl_driver (&str->ccl, (src ? (unsigned char *)src : (unsigned char*)""), + dst, n, 0, CCL_MODE_DECODING); break; case CODESYS_ISO2022: decode_coding_iso2022 (decoding, src, dst, n); @@ -2290,7 +2505,7 @@ BUFFER defaults to the current buffer if unspecified. char tempbuf[1024]; /* some random amount */ Bufpos newpos, even_newer_pos; Bufpos oldpos = lisp_buffer_stream_startpos (istr); - int size_in_bytes = Lstream_read (istr, tempbuf, sizeof (tempbuf)); + Lstream_data_count size_in_bytes = Lstream_read (istr, tempbuf, sizeof (tempbuf)); if (!size_in_bytes) break; @@ -2375,9 +2590,9 @@ struct encoding_stream #endif /* MULE */ }; -static int encoding_reader (Lstream *stream, unsigned char *data, size_t size); -static int encoding_writer (Lstream *stream, CONST unsigned char *data, - size_t size); +static Lstream_data_count encoding_reader (Lstream *stream, unsigned char *data, Lstream_data_count size); +static Lstream_data_count encoding_writer (Lstream *stream, const unsigned char *data, + Lstream_data_count size); static int encoding_rewinder (Lstream *stream); static int encoding_seekable_p (Lstream *stream); static int encoding_flusher (Lstream *stream); @@ -2409,12 +2624,12 @@ encoding_marker (Lisp_Object stream) /* Read SIZE bytes of data and store it into DATA. We are a encoding stream so we read data from the other end, encode it, and store it into DATA. */ -static int -encoding_reader (Lstream *stream, unsigned char *data, size_t size) +static Lstream_data_count +encoding_reader (Lstream *stream, unsigned char *data, Lstream_data_count size) { struct encoding_stream *str = ENCODING_STREAM_DATA (stream); unsigned char *orig_data = data; - int read_size; + Lstream_data_count read_size; int error_occurred = 0; /* We need to interface to mule_encode(), which expects to take some @@ -2471,11 +2686,11 @@ encoding_reader (Lstream *stream, unsigned char *data, size_t size) return data - orig_data; } -static int -encoding_writer (Lstream *stream, CONST unsigned char *data, size_t size) +static Lstream_data_count +encoding_writer (Lstream *stream, const unsigned char *data, Lstream_data_count size) { struct encoding_stream *str = ENCODING_STREAM_DATA (stream); - int retval; + Lstream_data_count retval; /* Encode all our data into the runoff, and then attempt to write it all out to the other end. Remove whatever chunk we succeeded @@ -2583,7 +2798,7 @@ set_encoding_stream_coding_system (Lstream *lstr, Lisp_Object codesys) static Lisp_Object make_encoding_stream_1 (Lstream *stream, Lisp_Object codesys, - CONST char *mode) + const char *mode) { Lstream *lstr = Lstream_new (lstream_encoding, mode); struct encoding_stream *str = ENCODING_STREAM_DATA (lstr); @@ -2614,8 +2829,8 @@ make_encoding_output_stream (Lstream *stream, Lisp_Object codesys) Store the encoded data into DST. */ static void -mule_encode (Lstream *encoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +mule_encode (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { struct encoding_stream *str = ENCODING_STREAM_DATA (encoding); @@ -2647,7 +2862,10 @@ mule_encode (Lstream *encoding, CONST unsigned char *src, break; case CODESYS_CCL: str->ccl.last_block = str->flags & CODING_STATE_END; - ccl_driver (&str->ccl, src, dst, n, 0, CCL_MODE_ENCODING); + /* When applying ccl program to stream, MUST NOT set NULL + pointer to src. */ + ccl_driver (&str->ccl, ((src) ? src : (unsigned char*)""), + dst, n, 0, CCL_MODE_ENCODING); break; case CODESYS_ISO2022: encode_coding_iso2022 (encoding, src, dst, n); @@ -2698,7 +2916,7 @@ text. BUFFER defaults to the current buffer if unspecified. char tempbuf[1024]; /* some random amount */ Bufpos newpos, even_newer_pos; Bufpos oldpos = lisp_buffer_stream_startpos (istr); - int size_in_bytes = Lstream_read (istr, tempbuf, sizeof (tempbuf)); + Lstream_data_count size_in_bytes = Lstream_read (istr, tempbuf, sizeof (tempbuf)); if (!size_in_bytes) break; @@ -2761,14 +2979,11 @@ text. BUFFER defaults to the current buffer if unspecified. ((c) >= 0xA1 && (c) <= 0xDF) static int -detect_coding_sjis (struct detection_state *st, CONST unsigned char *src, - unsigned int n) +detect_coding_sjis (struct detection_state *st, const Extbyte *src, Lstream_data_count n) { - int c; - while (n--) { - c = *src++; + unsigned char c = *(unsigned char *)src++; if (c == ISO_CODE_ESC || c == ISO_CODE_SI || c == ISO_CODE_SO) return 0; if (st->shift_jis.in_second_byte) @@ -2786,10 +3001,9 @@ detect_coding_sjis (struct detection_state *st, CONST unsigned char *src, /* Convert Shift-JIS data to internal format. */ static void -decode_coding_sjis (Lstream *decoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +decode_coding_sjis (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { - unsigned char c; struct decoding_stream *str = DECODING_STREAM_DATA (decoding); unsigned int flags = str->flags; unsigned int ch = str->ch; @@ -2797,7 +3011,7 @@ decode_coding_sjis (Lstream *decoding, CONST unsigned char *src, while (n--) { - c = *src++; + unsigned char c = *(unsigned char *)src++; if (ch) { @@ -2843,10 +3057,9 @@ decode_coding_sjis (Lstream *decoding, CONST unsigned char *src, /* Convert internally-formatted data to Shift-JIS. */ static void -encode_coding_sjis (Lstream *encoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +encode_coding_sjis (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { - unsigned char c; struct encoding_stream *str = ENCODING_STREAM_DATA (encoding); unsigned int flags = str->flags; unsigned int ch = str->ch; @@ -2854,7 +3067,7 @@ encode_coding_sjis (Lstream *encoding, CONST unsigned char *src, while (n--) { - c = *src++; + Bufbyte c = *src++; if (c == '\n') { if (eol_type != EOL_LF && eol_type != EOL_AUTODETECT) @@ -2923,16 +3136,16 @@ Return the corresponding character. } DEFUN ("encode-shift-jis-char", Fencode_shift_jis_char, 1, 1, 0, /* -Encode a JISX0208 character CHAR to SHIFT-JIS coding-system. +Encode a JISX0208 character CHARACTER to SHIFT-JIS coding-system. Return the corresponding character code in SHIFT-JIS as a cons of two bytes. */ - (ch)) + (character)) { Lisp_Object charset; int c1, c2, s1, s2; - CHECK_CHAR_COERCE_INT (ch); - BREAKUP_CHAR (XCHAR (ch), charset, c1, c2); + CHECK_CHAR_COERCE_INT (character); + BREAKUP_CHAR (XCHAR (character), charset, c1, c2); if (EQ (charset, Vcharset_japanese_jisx0208)) { ENCODE_SJIS (c1 | 0x80, c2 | 0x80, s1, s2); @@ -3047,14 +3260,11 @@ Return the corresponding character code in SHIFT-JIS as a cons of two bytes. } while (0) static int -detect_coding_big5 (struct detection_state *st, CONST unsigned char *src, - unsigned int n) +detect_coding_big5 (struct detection_state *st, const Extbyte *src, Lstream_data_count n) { - int c; - while (n--) { - c = *src++; + unsigned char c = *(unsigned char *)src++; if (c == ISO_CODE_ESC || c == ISO_CODE_SI || c == ISO_CODE_SO || (c >= 0x80 && c <= 0xA0)) return 0; @@ -3073,10 +3283,9 @@ detect_coding_big5 (struct detection_state *st, CONST unsigned char *src, /* Convert Big5 data to internal format. */ static void -decode_coding_big5 (Lstream *decoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +decode_coding_big5 (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { - unsigned char c; struct decoding_stream *str = DECODING_STREAM_DATA (decoding); unsigned int flags = str->flags; unsigned int ch = str->ch; @@ -3084,7 +3293,7 @@ decode_coding_big5 (Lstream *decoding, CONST unsigned char *src, while (n--) { - c = *src++; + unsigned char c = *(unsigned char *)src++; if (ch) { /* Previous character was first byte of Big5 char. */ @@ -3123,8 +3332,8 @@ decode_coding_big5 (Lstream *decoding, CONST unsigned char *src, /* Convert internally-formatted data to Big5. */ static void -encode_coding_big5 (Lstream *encoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +encode_coding_big5 (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { unsigned char c; struct encoding_stream *str = ENCODING_STREAM_DATA (encoding); @@ -3211,16 +3420,16 @@ Return the corresponding character. } DEFUN ("encode-big5-char", Fencode_big5_char, 1, 1, 0, /* -Encode the Big5 character CH to BIG5 coding-system. +Encode the Big5 character CHARACTER in the BIG5 coding-system. Return the corresponding character code in Big5. */ - (ch)) + (character)) { Lisp_Object charset; int c1, c2, b1, b2; - CHECK_CHAR_COERCE_INT (ch); - BREAKUP_CHAR (XCHAR (ch), charset, c1, c2); + CHECK_CHAR_COERCE_INT (character); + BREAKUP_CHAR (XCHAR (character), charset, c1, c2); if (EQ (charset, Vcharset_chinese_big5_1) || EQ (charset, Vcharset_chinese_big5_2)) { @@ -3248,13 +3457,13 @@ Return T on success, NIL on failure. */ (code, character)) { - unsigned int c; + size_t c; CHECK_CHAR (character); - CHECK_INT (code); + CHECK_NATNUM (code); c = XINT (code); - if (c < sizeof (fcd->ucs_to_mule_table)) + if (c < countof (fcd->ucs_to_mule_table)) { fcd->ucs_to_mule_table[c] = character; return Qt; @@ -3266,7 +3475,7 @@ Return T on success, NIL on failure. static Lisp_Object ucs_to_char (unsigned long code) { - if (code < sizeof (fcd->ucs_to_mule_table)) + if (code < countof (fcd->ucs_to_mule_table)) { return fcd->ucs_to_mule_table[code]; } @@ -3390,12 +3599,11 @@ encode_ucs4 (Lisp_Object charset, } static int -detect_coding_ucs4 (struct detection_state *st, CONST unsigned char *src, - unsigned int n) +detect_coding_ucs4 (struct detection_state *st, const Extbyte *src, Lstream_data_count n) { while (n--) { - int c = *src++; + unsigned char c = *(unsigned char *)src++; switch (st->ucs4.in_byte) { case 0: @@ -3415,8 +3623,8 @@ detect_coding_ucs4 (struct detection_state *st, CONST unsigned char *src, } static void -decode_coding_ucs4 (Lstream *decoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +decode_coding_ucs4 (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { struct decoding_stream *str = DECODING_STREAM_DATA (decoding); unsigned int flags = str->flags; @@ -3425,7 +3633,7 @@ decode_coding_ucs4 (Lstream *decoding, CONST unsigned char *src, while (n--) { - unsigned char c = *src++; + unsigned char c = *(unsigned char *)src++; switch (counter) { case 0: @@ -3451,8 +3659,8 @@ decode_coding_ucs4 (Lstream *decoding, CONST unsigned char *src, } static void -encode_coding_ucs4 (Lstream *encoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +encode_coding_ucs4 (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { struct encoding_stream *str = ENCODING_STREAM_DATA (encoding); unsigned int flags = str->flags; @@ -3464,7 +3672,7 @@ encode_coding_ucs4 (Lstream *encoding, CONST unsigned char *src, /* flags for handling composite chars. We do a little switcharoo on the source while we're outputting the composite char. */ unsigned int saved_n = 0; - CONST unsigned char *saved_src = NULL; + const unsigned char *saved_src = NULL; int in_composite = 0; back_to_square_n: @@ -3517,9 +3725,9 @@ encode_coding_ucs4 (Lstream *encoding, CONST unsigned char *src, { /* #### Bother! We don't know how to handle this yet. */ - Dynarr_add (dst, 0); - Dynarr_add (dst, 0); - Dynarr_add (dst, 0); + Dynarr_add (dst, '\0'); + Dynarr_add (dst, '\0'); + Dynarr_add (dst, '\0'); Dynarr_add (dst, '~'); } else @@ -3590,12 +3798,11 @@ encode_coding_ucs4 (Lstream *encoding, CONST unsigned char *src, /************************************************************************/ static int -detect_coding_utf8 (struct detection_state *st, CONST unsigned char *src, - unsigned int n) +detect_coding_utf8 (struct detection_state *st, const Extbyte *src, Lstream_data_count n) { while (n--) { - unsigned char c = *src++; + unsigned char c = *(unsigned char *)src++; switch (st->utf8.in_byte) { case 0: @@ -3625,8 +3832,8 @@ detect_coding_utf8 (struct detection_state *st, CONST unsigned char *src, } static void -decode_coding_utf8 (Lstream *decoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +decode_coding_utf8 (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { struct decoding_stream *str = DECODING_STREAM_DATA (decoding); unsigned int flags = str->flags; @@ -3636,7 +3843,7 @@ decode_coding_utf8 (Lstream *decoding, CONST unsigned char *src, while (n--) { - unsigned char c = *src++; + unsigned char c = *(unsigned char *)src++; switch (counter) { case 0: @@ -3739,8 +3946,8 @@ encode_utf8 (Lisp_Object charset, } static void -encode_coding_utf8 (Lstream *encoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +encode_coding_utf8 (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { struct encoding_stream *str = ENCODING_STREAM_DATA (encoding); unsigned int flags = str->flags; @@ -3753,12 +3960,12 @@ encode_coding_utf8 (Lstream *encoding, CONST unsigned char *src, /* flags for handling composite chars. We do a little switcharoo on the source while we're outputting the composite char. */ unsigned int saved_n = 0; - CONST unsigned char *saved_src = NULL; + const unsigned char *saved_src = NULL; int in_composite = 0; back_to_square_n: #endif /* ENABLE_COMPOSITE_CHARS */ - + while (n--) { unsigned char c = *src++; @@ -4092,7 +4299,48 @@ fit_to_be_escape_quoted (unsigned char c) If CHECK_INVALID_CHARSETS is non-zero, check for designation or invocation of an invalid character set and treat that as - an unrecognized escape sequence. */ + an unrecognized escape sequence. + + ******************************************************************** + + #### Strategies for error annotation and coding orthogonalization + + We really want to separate out a number of things. Conceptually, + there is a nested syntax. + + At the top level is the ISO 2022 extension syntax, including charset + designation and invocation, and certain auxiliary controls such as the + ISO 6429 direction specification. These are octet-oriented, with the + single exception (AFAIK) of the "exit Unicode" sequence which uses the + UTF's natural width (1 byte for UTF-7 and UTF-8, 2 bytes for UCS-2 and + UTF-16, and 4 bytes for UCS-4 and UTF-32). This will be treated as a + (deprecated) special case in Unicode processing. + + The middle layer is ISO 2022 character interpretation. This will depend + on the current state of the ISO 2022 registers, and assembles octets + into the character's internal representation. + + The lowest level is translating system control conventions. At present + this is restricted to newline translation, but one could imagine doing + tab conversion or line wrapping here. "Escape from Unicode" processing + would be done at this level. + + At each level the parser will verify the syntax. In the case of a + syntax error or warning (such as a redundant escape sequence that affects + no characters), the parser will take some action, typically inserting the + erroneous octets directly into the output and creating an annotation + which can be used by higher level I/O to mark the affected region. + + This should make it possible to do something sensible about separating + newline convention processing from character construction, and about + preventing ISO 2022 escape sequences from being recognized + inappropriately. + + The basic strategy will be to have octet classification tables, and + switch processing according to the table entry. + + It's possible that, by doing the processing with tables of functions or + the like, the parser can be used for both detection and translation. */ static int parse_iso2022_esc (Lisp_Object codesys, struct iso2022_decoder *iso, @@ -4362,6 +4610,7 @@ parse_iso2022_esc (Lisp_Object codesys, struct iso2022_decoder *iso, { /* Can this ever be reached? -slb */ abort(); + return 0; } cs = CHARSET_BY_ATTRIBUTES (type, c, @@ -4457,8 +4706,7 @@ parse_iso2022_esc (Lisp_Object codesys, struct iso2022_decoder *iso, } static int -detect_coding_iso2022 (struct detection_state *st, CONST unsigned char *src, - unsigned int n) +detect_coding_iso2022 (struct detection_state *st, const Extbyte *src, Lstream_data_count n) { int mask; @@ -4488,7 +4736,7 @@ detect_coding_iso2022 (struct detection_state *st, CONST unsigned char *src, while (n--) { - int c = *src++; + unsigned char c = *(unsigned char *)src++; if (c >= 0xA0) { mask &= ~CODING_CATEGORY_ISO_7_MASK; @@ -4648,8 +4896,8 @@ ensure_correct_direction (int direction, Lisp_Coding_System *codesys, /* Convert ISO2022-format data to internal format. */ static void -decode_coding_iso2022 (Lstream *decoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +decode_coding_iso2022 (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { struct decoding_stream *str = DECODING_STREAM_DATA (decoding); unsigned int flags = str->flags; @@ -4669,7 +4917,7 @@ decode_coding_iso2022 (Lstream *decoding, CONST unsigned char *src, while (n--) { - unsigned char c = *src++; + unsigned char c = *(unsigned char *)src++; if (flags & CODING_STATE_ESCAPE) { /* Within ESC sequence */ int retval = parse_iso2022_esc (coding_system, &str->iso2022, @@ -4889,8 +5137,8 @@ static void iso2022_designate (Lisp_Object charset, unsigned char reg, struct encoding_stream *str, unsigned_char_dynarr *dst) { - static CONST char inter94[] = "()*+"; - static CONST char inter96[] = ",-./"; + static const char inter94[] = "()*+"; + static const char inter96[] = ",-./"; unsigned int type; unsigned char final; Lisp_Object old_charset = str->iso2022.charset[reg]; @@ -4974,8 +5222,8 @@ ensure_shift_out (struct encoding_stream *str, unsigned_char_dynarr *dst) /* Convert internally-formatted data to ISO2022 format. */ static void -encode_coding_iso2022 (Lstream *encoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +encode_coding_iso2022 (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { unsigned char charmask, c; unsigned char char_boundary; @@ -4992,7 +5240,7 @@ encode_coding_iso2022 (Lstream *encoding, CONST unsigned char *src, /* flags for handling composite chars. We do a little switcharoo on the source while we're outputting the composite char. */ unsigned int saved_n = 0; - CONST unsigned char *saved_src = NULL; + const unsigned char *saved_src = NULL; int in_composite = 0; #endif /* ENABLE_COMPOSITE_CHARS */ @@ -5283,10 +5531,9 @@ encode_coding_iso2022 (Lstream *encoding, CONST unsigned char *src, contain all 256 possible byte values and that are not to be interpreted as being in any particular decoding. */ static void -decode_coding_no_conversion (Lstream *decoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +decode_coding_no_conversion (Lstream *decoding, const Extbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { - unsigned char c; struct decoding_stream *str = DECODING_STREAM_DATA (decoding); unsigned int flags = str->flags; unsigned int ch = str->ch; @@ -5294,7 +5541,7 @@ decode_coding_no_conversion (Lstream *decoding, CONST unsigned char *src, while (n--) { - c = *src++; + unsigned char c = *(unsigned char *)src++; DECODE_HANDLE_EOL_TYPE (eol_type, c, flags, dst); DECODE_ADD_BINARY_CHAR (c, dst); @@ -5308,8 +5555,8 @@ decode_coding_no_conversion (Lstream *decoding, CONST unsigned char *src, } static void -encode_coding_no_conversion (Lstream *encoding, CONST unsigned char *src, - unsigned_char_dynarr *dst, unsigned int n) +encode_coding_no_conversion (Lstream *encoding, const Bufbyte *src, + unsigned_char_dynarr *dst, Lstream_data_count n) { unsigned char c; struct encoding_stream *str = ENCODING_STREAM_DATA (encoding); @@ -5362,163 +5609,7 @@ encode_coding_no_conversion (Lstream *encoding, CONST unsigned char *src, } -/************************************************************************/ -/* Simple internal/external functions */ -/************************************************************************/ - -static Extbyte_dynarr *conversion_out_dynarr; -static Bufbyte_dynarr *conversion_in_dynarr; - -/* Determine coding system from coding format */ - -/* #### not correct for all values of `fmt'! */ -static Lisp_Object -external_data_format_to_coding_system (enum external_data_format fmt) -{ - switch (fmt) - { - case FORMAT_FILENAME: - case FORMAT_TERMINAL: - if (EQ (Vfile_name_coding_system, Qnil) || - EQ (Vfile_name_coding_system, Qbinary)) - return Qnil; - else - return Fget_coding_system (Vfile_name_coding_system); -#ifdef MULE - case FORMAT_CTEXT: - return Fget_coding_system (Qctext); -#endif - default: - return Qnil; - } -} - -Extbyte * -convert_to_external_format (CONST Bufbyte *ptr, - Bytecount len, - Extcount *len_out, - enum external_data_format fmt) -{ - Lisp_Object coding_system = external_data_format_to_coding_system (fmt); - - if (!conversion_out_dynarr) - conversion_out_dynarr = Dynarr_new (Extbyte); - else - Dynarr_reset (conversion_out_dynarr); - - if (NILP (coding_system)) - { - CONST Bufbyte *end = ptr + len; - - for (; ptr < end;) - { - Bufbyte c = - (BYTE_ASCII_P (*ptr)) ? *ptr : - (*ptr == LEADING_BYTE_CONTROL_1) ? (*(ptr+1) - 0x20) : - (*ptr == LEADING_BYTE_LATIN_ISO8859_1) ? (*(ptr+1)) : - '~'; - - Dynarr_add (conversion_out_dynarr, (Extbyte) c); - INC_CHARPTR (ptr); - } - -#ifdef ERROR_CHECK_BUFPOS - assert (ptr == end); -#endif - } - else - { - Lisp_Object instream, outstream, da_outstream; - Lstream *istr, *ostr; - struct gcpro gcpro1, gcpro2, gcpro3; - char tempbuf[1024]; /* some random amount */ - - instream = make_fixed_buffer_input_stream ((unsigned char *) ptr, len); - da_outstream = make_dynarr_output_stream - ((unsigned_char_dynarr *) conversion_out_dynarr); - outstream = - make_encoding_output_stream (XLSTREAM (da_outstream), coding_system); - istr = XLSTREAM (instream); - ostr = XLSTREAM (outstream); - GCPRO3 (instream, outstream, da_outstream); - while (1) - { - int size_in_bytes = Lstream_read (istr, tempbuf, sizeof (tempbuf)); - if (!size_in_bytes) - break; - Lstream_write (ostr, tempbuf, size_in_bytes); - } - Lstream_close (istr); - Lstream_close (ostr); - UNGCPRO; - Lstream_delete (istr); - Lstream_delete (ostr); - Lstream_delete (XLSTREAM (da_outstream)); - } - - *len_out = Dynarr_length (conversion_out_dynarr); - Dynarr_add (conversion_out_dynarr, 0); /* remember to zero-terminate! */ - return Dynarr_atp (conversion_out_dynarr, 0); -} -Bufbyte * -convert_from_external_format (CONST Extbyte *ptr, - Extcount len, - Bytecount *len_out, - enum external_data_format fmt) -{ - Lisp_Object coding_system = external_data_format_to_coding_system (fmt); - - if (!conversion_in_dynarr) - conversion_in_dynarr = Dynarr_new (Bufbyte); - else - Dynarr_reset (conversion_in_dynarr); - - if (NILP (coding_system)) - { - CONST Extbyte *end = ptr + len; - for (; ptr < end; ptr++) - { - Extbyte c = *ptr; - DECODE_ADD_BINARY_CHAR (c, conversion_in_dynarr); - } - } - else - { - Lisp_Object instream, outstream, da_outstream; - Lstream *istr, *ostr; - struct gcpro gcpro1, gcpro2, gcpro3; - char tempbuf[1024]; /* some random amount */ - - instream = make_fixed_buffer_input_stream ((unsigned char *) ptr, len); - da_outstream = make_dynarr_output_stream - ((unsigned_char_dynarr *) conversion_in_dynarr); - outstream = - make_decoding_output_stream (XLSTREAM (da_outstream), coding_system); - istr = XLSTREAM (instream); - ostr = XLSTREAM (outstream); - GCPRO3 (instream, outstream, da_outstream); - while (1) - { - int size_in_bytes = Lstream_read (istr, tempbuf, sizeof (tempbuf)); - if (!size_in_bytes) - break; - Lstream_write (ostr, tempbuf, size_in_bytes); - } - Lstream_close (istr); - Lstream_close (ostr); - UNGCPRO; - Lstream_delete (istr); - Lstream_delete (ostr); - Lstream_delete (XLSTREAM (da_outstream)); - } - - *len_out = Dynarr_length (conversion_in_dynarr); - Dynarr_add (conversion_in_dynarr, 0); /* remember to zero-terminate! */ - return Dynarr_atp (conversion_in_dynarr, 0); -} - - /************************************************************************/ /* Initialization */ /************************************************************************/ @@ -5526,8 +5617,9 @@ convert_from_external_format (CONST Extbyte *ptr, void syms_of_file_coding (void) { - deferror (&Qcoding_system_error, "coding-system-error", - "Coding-system error", Qio_error); + INIT_LRECORD_IMPLEMENTATION (coding_system); + + DEFERROR_STANDARD (Qcoding_system_error, Qio_error); DEFSUBR (Fcoding_system_p); DEFSUBR (Ffind_coding_system); @@ -5536,6 +5628,9 @@ syms_of_file_coding (void) DEFSUBR (Fcoding_system_name); DEFSUBR (Fmake_coding_system); DEFSUBR (Fcopy_coding_system); + DEFSUBR (Fcoding_system_canonical_name_p); + DEFSUBR (Fcoding_system_alias_p); + DEFSUBR (Fcoding_system_aliasee); DEFSUBR (Fdefine_coding_system_alias); DEFSUBR (Fsubsidiary_coding_system); @@ -5611,7 +5706,6 @@ syms_of_file_coding (void) defsymbol (&Qdecode, "decode"); #ifdef MULE - defsymbol (&Qctext, "ctext"); defsymbol (&coding_category_symbol[CODING_CATEGORY_SHIFT_JIS], "shift-jis"); defsymbol (&coding_category_symbol[CODING_CATEGORY_BIG5], @@ -5661,10 +5755,10 @@ vars_of_file_coding (void) int i; fcd = xnew (struct file_coding_dump); - dumpstruct (&fcd, &fcd_description); + dump_add_root_struct_ptr (&fcd, &fcd_description); /* Initialize to something reasonable ... */ - for (i = 0; i <= CODING_CATEGORY_LAST; i++) + for (i = 0; i < CODING_CATEGORY_LAST; i++) { fcd->coding_category_system[i] = Qnil; fcd->coding_category_by_priority[i] = i; @@ -5685,24 +5779,24 @@ Not used under a windowing system. Vterminal_coding_system = Qnil; DEFVAR_LISP ("coding-system-for-read", &Vcoding_system_for_read /* -Overriding coding system used when writing a file or process. -You should *bind* this, not set it. If this is non-nil, it specifies -the coding system that will be used when a file or process is read -in, and overrides `buffer-file-coding-system-for-read', +Overriding coding system used when reading from a file or process. +You should bind this variable with `let', but do not set it globally. +If this is non-nil, it specifies the coding system that will be used +to decode input on read operations, such as from a file or process. +It overrides `buffer-file-coding-system-for-read', `insert-file-contents-pre-hook', etc. Use those variables instead of -this one for permanent changes to the environment. -*/ ); +this one for permanent changes to the environment. */ ); Vcoding_system_for_read = Qnil; DEFVAR_LISP ("coding-system-for-write", &Vcoding_system_for_write /* -Overriding coding system used when writing a file or process. -You should *bind* this, not set it. If this is non-nil, it specifies -the coding system that will be used when a file or process is wrote -in, and overrides `buffer-file-coding-system', -`write-region-pre-hook', etc. Use those variables instead of this one -for permanent changes to the environment. -*/ ); +Overriding coding system used when writing to a file or process. +You should bind this variable with `let', but do not set it globally. +If this is non-nil, it specifies the coding system that will be used +to encode output for write operations, such as to a file or process. +It overrides `buffer-file-coding-system', `write-region-pre-hook', etc. +Use those variables instead of this one for permanent changes to the +environment. */ ); Vcoding_system_for_write = Qnil; DEFVAR_LISP ("file-name-coding-system", &Vfile_name_coding_system /* @@ -5728,7 +5822,7 @@ complex_vars_of_file_coding (void) make_lisp_hash_table (50, HASH_TABLE_NON_WEAK, HASH_TABLE_EQ); the_codesys_prop_dynarr = Dynarr_new (codesys_prop); - dumpstruct (&the_codesys_prop_dynarr, &codesys_prop_dynarr_description); + dump_add_root_struct_ptr (&the_codesys_prop_dynarr, &codesys_prop_dynarr_description); #define DEFINE_CODESYS_PROP(Prop_Type, Sym) do \ { \ @@ -5781,15 +5875,20 @@ complex_vars_of_file_coding (void) Fdefine_coding_system_alias (Qno_conversion, Qraw_text); + Fdefine_coding_system_alias (Qfile_name, Qbinary); + + Fdefine_coding_system_alias (Qterminal, Qbinary); + Fdefine_coding_system_alias (Qkeyboard, Qbinary); + /* Need this for bootstrapping */ fcd->coding_category_system[CODING_CATEGORY_NO_CONVERSION] = Fget_coding_system (Qraw_text); #ifdef MULE { - unsigned int i; + size_t i; - for (i = 0; i < 65536; i++) + for (i = 0; i < countof (fcd->ucs_to_mule_table); i++) fcd->ucs_to_mule_table[i] = Qnil; } staticpro (&mule_to_ucs_table);