updated for version 7.0102
diff --git a/src/Make_mvc.mak b/src/Make_mvc.mak
index e74019f..144f956 100644
--- a/src/Make_mvc.mak
+++ b/src/Make_mvc.mak
@@ -683,7 +683,7 @@
 
 $(VIM).exe: $(OUTDIR) $(OBJ) $(GUI_OBJ) $(OLE_OBJ) $(OLE_IDL) $(MZSCHEME_OBJ) $(PERL_OBJ) $(PYTHON_OBJ) $(RUBY_OBJ) $(TCL_OBJ) $(SNIFF_OBJ) $(CSCOPE_OBJ) $(NETBEANS_OBJ) $(XPM_OBJ) version.c version.h
 	$(CC) $(CFLAGS)  version.c /Fo$(OUTDIR)/version.obj $(PDB)
-	$(link) $(LINKARGS1) -out:$* $(OBJ) $(GUI_OBJ) $(OLE_OBJ) \
+	$(link) $(LINKARGS1) -out:$(VIM).exe $(OBJ) $(GUI_OBJ) $(OLE_OBJ) \
 		$(MZSCHEME_OBJ) $(PERL_OBJ) $(PYTHON_OBJ) $(RUBY_OBJ) $(TCL_OBJ) $(SNIFF_OBJ) \
 		$(CSCOPE_OBJ) $(NETBEANS_OBJ) $(XPM_OBJ) \
 		$(OUTDIR)\version.obj $(LINKARGS2)
diff --git a/src/option.c b/src/option.c
index 57d2951..dfe2e2b 100644
--- a/src/option.c
+++ b/src/option.c
@@ -2036,7 +2036,7 @@
     {"spellcapcheck", "spc", P_STRING|P_ALLOCED|P_VI_DEF|P_SECURE|P_RBUF,
 #ifdef FEAT_SYN_HL
 			    (char_u *)&p_spc, PV_SPC,
-			    {(char_u *)"[.?!][])'\" \\t\\n]\\+", (char_u *)0L}
+			    {(char_u *)"[.?!]\\_[\\])'\"	 ]\\+", (char_u *)0L}
 #else
 			    (char_u *)NULL, PV_NONE,
 			    {(char_u *)0L, (char_u *)0L}
@@ -2605,7 +2605,7 @@
 static char_u *check_clipboard_option __ARGS((void));
 #endif
 #ifdef FEAT_SYN_HL
-static char_u *compile_cap_prog __ARGS((void));
+static char_u *compile_cap_prog __ARGS((buf_T *buf));
 #endif
 static char_u *set_bool_option __ARGS((int opt_idx, char_u *varp, int value, int opt_flags));
 static char_u *set_num_option __ARGS((int opt_idx, char_u *varp, long value, char_u *errbuf, size_t errbuflen, int opt_flags));
@@ -4610,7 +4610,7 @@
 #endif
 #ifdef FEAT_SYN_HL
     (void)spell_check_sps();
-    (void)compile_cap_prog();
+    (void)compile_cap_prog(curbuf);
 #endif
 #if defined(FEAT_TOOLBAR) && !defined(FEAT_GUI_W32)
     (void)opt_strings_flags(p_toolbar, p_toolbar_values, &toolbar_flags, TRUE);
@@ -5774,7 +5774,7 @@
     /* When 'spellcapcheck' is set compile the regexp program. */
     else if (varp == &(curbuf->b_p_spc))
     {
-	errmsg = compile_cap_prog();
+	errmsg = compile_cap_prog(curbuf);
     }
     /* 'spellsuggest' */
     else if (varp == &p_sps)
@@ -6437,23 +6437,24 @@
  * Return error message when failed, NULL when OK.
  */
     static char_u *
-compile_cap_prog()
+compile_cap_prog(buf)
+    buf_T	*buf;
 {
-    regprog_T   *rp = curbuf->b_cap_prog;
+    regprog_T   *rp = buf->b_cap_prog;
 
-    if (*curbuf->b_p_spc == NUL)
+    if (*buf->b_p_spc == NUL)
     {
-	curbuf->b_cap_prog = NULL;
+	buf->b_cap_prog = NULL;
 	vim_free(rp);
 	return NULL;
     }
 
     /* Prepend a ^ so that we only match at one column */
-    vim_snprintf((char *)IObuff, IOSIZE, "^%s", curbuf->b_p_spc);
-    curbuf->b_cap_prog = vim_regcomp(IObuff, RE_MAGIC);
-    if (curbuf->b_cap_prog == NULL)
+    vim_snprintf((char *)IObuff, IOSIZE, "^%s", buf->b_p_spc);
+    buf->b_cap_prog = vim_regcomp(IObuff, RE_MAGIC);
+    if (buf->b_cap_prog == NULL)
     {
-	curbuf->b_cap_prog = rp;
+	buf->b_cap_prog = rp;
 	return e_invarg;
     }
 
@@ -8758,6 +8759,7 @@
 	    /* Don't copy 'syntax', it must be set */
 	    buf->b_p_syn = empty_option;
 	    buf->b_p_spc = vim_strsave(p_spc);
+	    (void)compile_cap_prog(buf);
 	    buf->b_p_spf = vim_strsave(p_spf);
 	    buf->b_p_spl = vim_strsave(p_spl);
 #endif
diff --git a/src/po/Make_cyg.mak b/src/po/Make_cyg.mak
new file mode 100644
index 0000000..f39368f
--- /dev/null
+++ b/src/po/Make_cyg.mak
@@ -0,0 +1,76 @@
+# Makefile for the Vim message translations for Cygwin
+# by Tony Mechelynck <antoine.mechelynck@skynet.be>
+# after Make_ming.mak by
+# Eduardo F. Amatria <eferna1@platea.pntic.mec.es>
+#
+# Read the README_ming.txt file before using it.
+#
+# Use at your own risk but with care, it could even kill your canary.
+#
+
+ifndef VIMRUNTIME
+VIMRUNTIME = ../../runtime
+endif
+
+LANGUAGES =	af ca cs de en_GB es fr ga it ja ko no pl ru sk sv uk vi zh_TW \
+		zh_TW.UTF-8 zh_CN zh_CN.UTF-8
+MOFILES =	af.mo ca.mo cs.mo de.mo en_GB.mo es.mo fr.mo ga.mo it.mo ja.mo \
+		ko.mo no.mo pl.mo ru.mo sk.mo sv.mo uk.mo vi.mo \
+		zh_TW.mo zh_TW.UTF-8.mo zh_CN.mo zh_CN.UTF-8.mo
+
+PACKAGE = vim
+
+# Uncomment one of the lines below or modify it to put the path to your
+# gettex binaries; I use the first
+ifndef GETTEXT_PATH
+#GETTEXT_PATH = C:/gettext.win32/bin/
+#GETTEXT_PATH = C:/gettext-0.10.35-w32/win32/Release/
+GETTEXT_PATH = /bin/
+endif
+
+MSGFMT = $(GETTEXT_PATH)msgfmt
+XGETTEXT = $(GETTEXT_PATH)xgettext
+MSGMERGE = $(GETTEXT_PATH)msgmerge
+
+# MV = move
+# CP = copy
+# RM = del
+# MKD = mkdir
+MV = mv -f
+CP = cp -f
+RM = rm -f
+MKD = mkdir -p
+
+.SUFFIXES:
+.SUFFIXES: .po .mo .pot
+.PHONY: first_time all install clean $(LANGUAGES)
+
+.po.mo:
+	$(MSGFMT) -o $@ $<
+
+all: $(MOFILES)
+
+first_time:
+	$(XGETTEXT) --default-domain=$(LANGUAGE) \
+		--add-comments --keyword=_ --keyword=N_ $(wildcard ../*.c) ../if_perl.xs $(wildcard ../globals.h)
+
+$(LANGUAGES):
+	$(XGETTEXT) --default-domain=$(PACKAGE) \
+		--add-comments --keyword=_ --keyword=N_ $(wildcard ../*.c) ../if_perl.xs $(wildcard ../globals.h)
+	$(MV) $(PACKAGE).po $(PACKAGE).pot
+	$(CP) $@.po $@.po.orig
+	$(MV) $@.po $@.po.old
+	$(MSGMERGE) $@.po.old $(PACKAGE).pot -o $@.po
+	$(RM) $@.po.old
+
+install: $(MOFILES)
+	for TARGET in $(LANGUAGES); do \
+		$(MKD) $(VIMRUNTIME)/lang/$$TARGET/LC_MESSAGES ; \
+		$(CP) $$TARGET.mo $(VIMRUNTIME)/lang/$$TARGET/LC_MESSAGES/$(PACKAGE).mo ; \
+	done
+
+clean:
+	$(RM) *.mo
+	$(RM) *.pot
+
+
diff --git a/src/spell.c b/src/spell.c
index 015a710..f23cf98 100644
--- a/src/spell.c
+++ b/src/spell.c
@@ -192,7 +192,10 @@
  * <flags>	1 byte	    bitmask of:
  *			    WF_ALLCAP	word must have only capitals
  *			    WF_ONECAP   first char of word must be capital
+ *			    WF_KEEPCAP	keep-case word
+ *			    WF_FIXCAP   keep-case word, all caps not allowed
  *			    WF_RARE	rare word
+ *			    WF_BANNED	bad word
  *			    WF_REGION	<region> follows
  *			    WF_PFX	<prefixID> follows
  *
@@ -241,9 +244,10 @@
 #define WF_RARE	    0x08	/* rare word */
 #define WF_BANNED   0x10	/* bad word */
 #define WF_PFX	    0x20	/* prefix ID list follows */
+#define WF_FIXCAP   0x40	/* keep-case word, allcap not allowed */
 #define WF_KEEPCAP  0x80	/* keep-case word */
 
-#define WF_CAPMASK (WF_ONECAP | WF_ALLCAP | WF_KEEPCAP)
+#define WF_CAPMASK (WF_ONECAP | WF_ALLCAP | WF_KEEPCAP | WF_FIXCAP)
 
 #define WF_RAREPFX  0x1000000	/* in sl_pidxs: flag for rare postponed
 				   prefix; must be above prefixID (one byte)
@@ -584,14 +588,14 @@
 static int valid_word_prefix __ARGS((int totprefcnt, int arridx, int prefid, char_u *word, slang_T *slang));
 static void find_prefix __ARGS((matchinf_T *mip));
 static int fold_more __ARGS((matchinf_T *mip));
-static int spell_valid_case __ARGS((int origflags, int treeflags));
+static int spell_valid_case __ARGS((int wordflags, int treeflags));
 static int no_spell_checking __ARGS((void));
 static void spell_load_lang __ARGS((char_u *lang));
 static char_u *spell_enc __ARGS((void));
 static void int_wordlist_spl __ARGS((char_u *fname));
 static void spell_load_cb __ARGS((char_u *fname, void *cookie));
 static slang_T *spell_load_file __ARGS((char_u *fname, char_u *lang, slang_T *old_lp, int silent));
-static char_u *read_cnt_string __ARGS((FILE *fd, int cnt_bytes, int *errp));
+static char_u *read_cnt_string __ARGS((FILE *fd, int cnt_bytes, int *lenp));
 static int set_sofo __ARGS((slang_T *lp, char_u *from, char_u *to));
 static void set_sal_first __ARGS((slang_T *lp));
 #ifdef FEAT_MBYTE
@@ -603,7 +607,7 @@
 static int find_region __ARGS((char_u *rp, char_u *region));
 static int captype __ARGS((char_u *word, char_u *end));
 static void spell_reload_one __ARGS((char_u *fname, int added_word));
-static int set_spell_charflags __ARGS((char_u *flags, char_u *upp));
+static int set_spell_charflags __ARGS((char_u *flags, int cnt, char_u *upp));
 static int set_spell_chartab __ARGS((char_u *fol, char_u *low, char_u *upp));
 static void write_spell_chartab __ARGS((FILE *fd));
 static int spell_casefold __ARGS((char_u *p, int len, char_u *buf, int buflen));
@@ -1293,13 +1297,13 @@
  * case.
  */
     static int
-spell_valid_case(origflags, treeflags)
-    int	    origflags;	    /* flags for the checked word. */
+spell_valid_case(wordflags, treeflags)
+    int	    wordflags;	    /* flags for the checked word. */
     int	    treeflags;	    /* flags for the word in the spell tree */
 {
-    return (origflags == WF_ALLCAP
+    return ((wordflags == WF_ALLCAP && (treeflags & WF_FIXCAP) == 0)
 	    || ((treeflags & (WF_ALLCAP | WF_KEEPCAP)) == 0
-		&& ((treeflags & WF_ONECAP) == 0 || origflags == WF_ONECAP)));
+		&& ((treeflags & WF_ONECAP) == 0 || wordflags == WF_ONECAP)));
 }
 
 /*
@@ -1837,12 +1841,12 @@
 
     /* <charflagslen> <charflags> */
     p = read_cnt_string(fd, 1, &cnt);
-    if (cnt == FAIL)
+    if (cnt < 0)
 	goto endFAIL;
 
     /* <fcharslen> <fchars> */
-    fol = read_cnt_string(fd, 2, &cnt);
-    if (cnt == FAIL)
+    fol = read_cnt_string(fd, 2, &ccnt);
+    if (ccnt < 0)
     {
 	vim_free(p);
 	goto endFAIL;
@@ -1850,7 +1854,7 @@
 
     /* Set the word-char flags and fill SPELL_ISUPPER() table. */
     if (p != NULL && fol != NULL)
-	i = set_spell_charflags(p, fol);
+	i = set_spell_charflags(p, cnt, fol);
 
     vim_free(p);
     vim_free(fol);
@@ -1861,7 +1865,7 @@
 
     /* <midwordlen> <midword> */
     lp->sl_midword = read_cnt_string(fd, 2, &cnt);
-    if (cnt == FAIL)
+    if (cnt < 0)
 	goto endFAIL;
 
     /* <prefcondcnt> <prefcond> ... */
@@ -1912,10 +1916,10 @@
     {
 	ftp = &((fromto_T *)gap->ga_data)[gap->ga_len];
 	ftp->ft_from = read_cnt_string(fd, 1, &i);
-	if (i == FAIL)
+	if (i <= 0)
 	    goto endFAIL;
 	ftp->ft_to = read_cnt_string(fd, 1, &i);
-	if (i == FAIL)
+	if (i <= 0)
 	{
 	    vim_free(ftp->ft_from);
 	    goto endFAIL;
@@ -1942,6 +1946,8 @@
 	lp->sl_rem_accents = TRUE;
     if (i & SAL_SOFO)
 	lp->sl_sofo = TRUE;
+    else
+	lp->sl_sofo = FALSE;
 
     cnt = (getc(fd) << 8) + getc(fd);		/* <salcount> */
     if (cnt < 0)
@@ -1957,19 +1963,24 @@
 
 	/* <salfromlen> <salfrom> */
 	bp = read_cnt_string(fd, 2, &cnt);
-	if (cnt == FAIL)
+	if (cnt < 0)
 	    goto endFAIL;
 
 	/* <saltolen> <salto> */
 	fol = read_cnt_string(fd, 2, &cnt);
-	if (cnt == FAIL)
+	if (cnt < 0)
 	{
 	    vim_free(bp);
 	    goto endFAIL;
 	}
 
 	/* Store the info in lp->sl_sal and/or lp->sl_sal_first. */
-	i = set_sofo(lp, bp, fol);
+	if (bp != NULL && fol != NULL)
+	    i = set_sofo(lp, bp, fol);
+	else if (bp != NULL || fol != NULL)
+	    i = FAIL;	    /* only one of two strings is an error */
+	else
+	    i = OK;
 
 	vim_free(bp);
 	vim_free(fol);
@@ -2036,7 +2047,7 @@
 
 	    /* <saltolen> <salto> */
 	    smp->sm_to = read_cnt_string(fd, 1, &ccnt);
-	    if (ccnt == FAIL)
+	    if (ccnt < 0)
 	    {
 		vim_free(smp->sm_lead);
 		goto formerr;
@@ -2052,10 +2063,13 @@
 		    smp->sm_oneof_w = NULL;
 		else
 		    smp->sm_oneof_w = mb_str2wide(smp->sm_oneof);
-		smp->sm_to_w = mb_str2wide(smp->sm_to);
+		if (smp->sm_to == NULL)
+		    smp->sm_to_w = NULL;
+		else
+		    smp->sm_to_w = mb_str2wide(smp->sm_to);
 		if (smp->sm_lead_w == NULL
 			|| (smp->sm_oneof_w == NULL && smp->sm_oneof != NULL)
-			|| smp->sm_to_w == NULL)
+			|| (smp->sm_to_w == NULL && smp->sm_to != NULL))
 		{
 		    vim_free(smp->sm_lead);
 		    vim_free(smp->sm_to);
@@ -2074,11 +2088,13 @@
 
     /* <maplen> <mapstr> */
     p = read_cnt_string(fd, 2, &cnt);
-    if (cnt == FAIL)
+    if (cnt < 0)
 	goto endFAIL;
-    set_map_str(lp, p);
-    vim_free(p);
-
+    if (p != NULL)
+    {
+	set_map_str(lp, p);
+	vim_free(p);
+    }
 
     /* round 1: <LWORDTREE>
      * round 2: <KWORDTREE>
@@ -2155,13 +2171,13 @@
  * Read a length field from "fd" in "cnt_bytes" bytes.
  * Allocate memory, read the string into it and add a NUL at the end.
  * Returns NULL when the count is zero.
- * Sets "*errp" to FAIL when there is an error, OK otherwise.
+ * Sets "*cntp" to -1 when there is an error, length of the result otherwise.
  */
     static char_u *
-read_cnt_string(fd, cnt_bytes, errp)
+read_cnt_string(fd, cnt_bytes, cntp)
     FILE	*fd;
     int		cnt_bytes;
-    int		*errp;
+    int		*cntp;
 {
     int		cnt = 0;
     int		i;
@@ -2173,18 +2189,20 @@
     if (cnt < 0)
     {
 	EMSG(_(e_spell_trunc));
-	*errp = FAIL;
+	*cntp = -1;
 	return NULL;
     }
+    *cntp = cnt;
+    if (cnt == 0)
+	return NULL;	    /* nothing to read, return NULL */
 
     /* allocate memory */
     str = alloc((unsigned)cnt + 1);
     if (str == NULL)
     {
-	*errp = FAIL;
+	*cntp = -1;
 	return NULL;
     }
-    *errp = OK;
 
     /* Read the string.  Doesn't check for truncated file. */
     for (i = 0; i < cnt; ++i)
@@ -2512,6 +2530,8 @@
     char_u	*p;
     int		round;
     char_u	*spf;
+    char_u	*use_region = NULL;
+    int		dont_use_region = FALSE;
 
     ga_init2(&ga, sizeof(langp_T), 2);
     clear_midword(buf);
@@ -2545,7 +2565,15 @@
 		region = lang + len - 2;
 		len -= 3;
 		lang[len] = NUL;
+
+		/* If the region differs from what was used before then don't
+		 * use it for 'spellfile'. */
+		if (use_region != NULL && STRCMP(region, use_region) != 0)
+		    dont_use_region = TRUE;
+		use_region = region;
 	    }
+	    else
+		dont_use_region = TRUE;
 
 	    /* Check if we loaded this language before. */
 	    for (lp = first_lang; lp != NULL; lp = lp->sl_next)
@@ -2576,7 +2604,15 @@
 		    c = find_region(lp->sl_regions, region);
 		    if (c == REGION_ALL)
 		    {
-			if (!lp->sl_add)
+			if (lp->sl_add)
+			{
+			    if (*lp->sl_regions != NUL)
+				/* This addition file is for other regions. */
+				region_mask = 0;
+			}
+			else
+			    /* This is probably an error.  Give a warning and
+			     * accept the words anyway. */
 			    smsg((char_u *)
 				    _("Warning: region %s not supported"),
 								      region);
@@ -2585,15 +2621,18 @@
 			region_mask = 1 << c;
 		}
 
-		if (ga_grow(&ga, 1) == FAIL)
+		if (region_mask != 0)
 		{
-		    ga_clear(&ga);
-		    return e_outofmem;
+		    if (ga_grow(&ga, 1) == FAIL)
+		    {
+			ga_clear(&ga);
+			return e_outofmem;
+		    }
+		    LANGP_ENTRY(ga, ga.ga_len)->lp_slang = lp;
+		    LANGP_ENTRY(ga, ga.ga_len)->lp_region = region_mask;
+		    ++ga.ga_len;
+		    use_midword(lp, buf);
 		}
-		LANGP_ENTRY(ga, ga.ga_len)->lp_slang = lp;
-		LANGP_ENTRY(ga, ga.ga_len)->lp_region = region_mask;
-		++ga.ga_len;
-		use_midword(lp, buf);
 	    }
     }
 
@@ -2649,10 +2688,25 @@
 	}
 	if (lp != NULL && ga_grow(&ga, 1) == OK)
 	{
-	    LANGP_ENTRY(ga, ga.ga_len)->lp_slang = lp;
-	    LANGP_ENTRY(ga, ga.ga_len)->lp_region = REGION_ALL;
-	    ++ga.ga_len;
-	    use_midword(lp, buf);
+	    region_mask = REGION_ALL;
+	    if (use_region != NULL && !dont_use_region)
+	    {
+		/* find region in sl_regions */
+		c = find_region(lp->sl_regions, use_region);
+		if (c != REGION_ALL)
+		    region_mask = 1 << c;
+		else if (*lp->sl_regions != NUL)
+		    /* This spell file is for other regions. */
+		    region_mask = 0;
+	    }
+
+	    if (region_mask != 0)
+	    {
+		LANGP_ENTRY(ga, ga.ga_len)->lp_slang = lp;
+		LANGP_ENTRY(ga, ga.ga_len)->lp_region = region_mask;
+		++ga.ga_len;
+		use_midword(lp, buf);
+	    }
 	}
     }
 
@@ -2697,6 +2751,9 @@
 {
     char_u	*p;
 
+    if (lp->sl_midword == NULL)	    /* there aren't any */
+	return;
+
     for (p = lp->sl_midword; *p != NUL; )
 #ifdef FEAT_MBYTE
 	if (has_mbyte)
@@ -3799,7 +3856,7 @@
 	     * for rare word (if defined). */
 	    if (affile->af_kep != NUL
 		    && vim_strchr(afflist, affile->af_kep) != NULL)
-		flags |= WF_KEEPCAP;
+		flags |= WF_KEEPCAP | WF_FIXCAP;
 	    if (affile->af_rar != NUL
 		    && vim_strchr(afflist, affile->af_rar) != NULL)
 		flags |= WF_RARE;
@@ -4150,6 +4207,9 @@
 		    {
 			spin->si_region_count = STRLEN(line) / 2;
 			STRCPY(spin->si_region_name, line);
+
+			/* Adjust the mask for a word valid in all regions. */
+			spin->si_region = (1 << spin->si_region_count) - 1;
 		    }
 		}
 		continue;
@@ -4171,7 +4231,7 @@
 	    while (*p != NUL)
 	    {
 		if (*p == '=')		/* keep-case word */
-		    flags |= WF_KEEPCAP;
+		    flags |= WF_KEEPCAP | WF_FIXCAP;
 		else if (*p == '!')	/* Bad, bad, wicked word. */
 		    flags |= WF_BANNED;
 		else if (*p == '?')	/* Rare word. */
@@ -5604,34 +5664,39 @@
  * Set the spell character tables from strings in the .spl file.
  */
     static int
-set_spell_charflags(flags, upp)
+set_spell_charflags(flags, cnt, fol)
     char_u	*flags;
-    char_u	*upp;
+    int		cnt;	    /* length of "flags" */
+    char_u	*fol;
 {
     /* We build the new tables here first, so that we can compare with the
      * previous one. */
     spelltab_T	new_st;
     int		i;
-    char_u	*p = upp;
+    char_u	*p = fol;
     int		c;
 
     clear_spell_chartab(&new_st);
 
-    for (i = 0; flags[i] != NUL; ++i)
+    for (i = 0; i < 128; ++i)
     {
-	new_st.st_isw[i + 128] = (flags[i] & CF_WORD) != 0;
-	new_st.st_isu[i + 128] = (flags[i] & CF_UPPER) != 0;
+	if (i < cnt)
+	{
+	    new_st.st_isw[i + 128] = (flags[i] & CF_WORD) != 0;
+	    new_st.st_isu[i + 128] = (flags[i] & CF_UPPER) != 0;
+	}
 
-	if (*p == NUL)
-	    return FAIL;
+	if (*p != NUL)
+	{
 #ifdef FEAT_MBYTE
-	c = mb_ptr2char_adv(&p);
+	    c = mb_ptr2char_adv(&p);
 #else
-	c = *p++;
+	    c = *p++;
 #endif
-	new_st.st_fold[i + 128] = c;
-	if (i + 128 != c && new_st.st_isu[i + 128] && c < 256)
-	    new_st.st_upper[c] = i + 128;
+	    new_st.st_fold[i + 128] = c;
+	    if (i + 128 != c && new_st.st_isu[i + 128] && c < 256)
+		new_st.st_upper[c] = i + 128;
+	}
     }
 
     return set_spell_finish(&new_st);
@@ -7992,6 +8057,8 @@
 		{
 		    byts = lp->lp_slang->sl_kbyts;
 		    idxs = lp->lp_slang->sl_kidxs;
+		    if (byts == NULL)	    /* no keep-case words */
+			continue;
 		}
 
 		depth = 0;
@@ -8836,6 +8903,8 @@
 
 		    /* replace string */
 		    s = smp[n].sm_to;
+		    if (s == NULL)
+			s = (char_u *)"";
 		    pf = smp[n].sm_rules;
 		    p0 = (vim_strchr(pf, '<') != NULL) ? 1 : 0;
 		    if (p0 == 1 && z == 0)
@@ -9138,18 +9207,20 @@
 		    if (p0 == 1 && z == 0)
 		    {
 			/* rule with '<' is used */
-			if (reslen > 0 && *ws != NUL && (wres[reslen - 1] == c
+			if (reslen > 0 && ws != NULL && *ws != NUL
+				&& (wres[reslen - 1] == c
 						    || wres[reslen - 1] == *ws))
 			    reslen--;
 			z0 = 1;
 			z = 1;
 			k0 = 0;
-			while (*ws != NUL && word[i + k0] != NUL)
-			{
-			    word[i + k0] = *ws;
-			    k0++;
-			    ws++;
-			}
+			if (ws != NULL)
+			    while (*ws != NUL && word[i + k0] != NUL)
+			    {
+				word[i + k0] = *ws;
+				k0++;
+				ws++;
+			    }
 			if (k > k0)
 			    mch_memmove(word + i + k0, word + i + k,
 				    sizeof(int) * (STRLEN(word + i + k) + 1));
@@ -9162,14 +9233,19 @@
 			/* no '<' rule used */
 			i += k - 1;
 			z = 0;
-			while (*ws != NUL && ws[1] != NUL && reslen < MAXWLEN)
-			{
-			    if (reslen == 0 || wres[reslen - 1] != *ws)
-				wres[reslen++] = *ws;
-			    ws++;
-			}
+			if (ws != NULL)
+			    while (*ws != NUL && ws[1] != NUL
+							  && reslen < MAXWLEN)
+			    {
+				if (reslen == 0 || wres[reslen - 1] != *ws)
+				    wres[reslen++] = *ws;
+				ws++;
+			    }
 			/* new "actual letter" */
-			c = *ws;
+			if (ws == NULL)
+			    c = NUL;
+			else
+			    c = *ws;
 			if (strstr((char *)s, "^^") != NULL)
 			{
 			    if (c != NUL)
@@ -9722,7 +9798,8 @@
     else
     {
 	p = word;
-	if (round == 2 && (captype(word, NULL) & WF_KEEPCAP) == 0)
+	if (round == 2 && ((captype(word, NULL) & WF_KEEPCAP) == 0
+						 || (flags & WF_FIXCAP) != 0))
 	    keepcap = TRUE;
     }
 
diff --git a/src/testdir/Make_amiga.mak b/src/testdir/Make_amiga.mak
index cfe2134..1c9d422 100644
--- a/src/testdir/Make_amiga.mak
+++ b/src/testdir/Make_amiga.mak
@@ -24,7 +24,7 @@
 		test38.out test39.out test40.out test41.out test42.out \
 		test43.out test44.out test45.out test46.out test47.out \
 		test48.out test51.out test53.out test54.out test55.out \
-		test56.out test57.out
+		test56.out test57.out test58.out
 
 .SUFFIXES: .in .out
 
@@ -101,3 +101,4 @@
 test55.out: test55.in
 test56.out: test56.in
 test57.out: test57.in
+test58.out: test58.in
diff --git a/src/testdir/Make_dos.mak b/src/testdir/Make_dos.mak
index 6ca1acc..1b3c772 100644
--- a/src/testdir/Make_dos.mak
+++ b/src/testdir/Make_dos.mak
@@ -18,7 +18,7 @@
 		test35.out test36.out test43.out \
 		test44.out test45.out test46.out test47.out \
 		test48.out test51.out test53.out test54.out \
-		test55.out test56.out test57.out
+		test55.out test56.out test57.out test58.out
 
 SCRIPTS =	test3.out test4.out test5.out test6.out test7.out \
 		test8.out test9.out test11.out test13.out test14.out \
diff --git a/src/testdir/Make_os2.mak b/src/testdir/Make_os2.mak
index 4d3296c..a771e6a 100644
--- a/src/testdir/Make_os2.mak
+++ b/src/testdir/Make_os2.mak
@@ -24,7 +24,7 @@
 		test38.out test39.out test40.out test41.out test42.out \
 		test43.out test44.out test45.out test46.out test47.out \
 		test48.out test51.out test53.out test54.out test55.out \
-		test56.out test57.out
+		test56.out test57.out test58.out
 
 .SUFFIXES: .in .out
 
diff --git a/src/testdir/Make_vms.mms b/src/testdir/Make_vms.mms
index 7df1d50..1ca1e8b 100644
--- a/src/testdir/Make_vms.mms
+++ b/src/testdir/Make_vms.mms
@@ -4,7 +4,7 @@
 # Authors:	Zoltan Arpadffy, <arpadffy@polarhome.com>
 #		Sandor Kopanyi,  <sandor.kopanyi@mailbox.hu>
 #
-# Last change:  2005 May 18
+# Last change:  2005 Jul 04
 #
 # This has been tested on VMS 6.2 to 7.2 on DEC Alpha and VAX.
 # Edit the lines in the Configuration section below to select.
@@ -58,7 +58,7 @@
 	 test38.out test39.out test40.out test41.out test42.out \
 	 test43.out test44.out test45.out test46.out \
 	 test48.out test51.out test53.out test54.out test55.out \
-	 test56.out
+	 test56.out test57.out test58.out
 
 .IFDEF WANT_GUI
 SCRIPT_GUI = test16.out
diff --git a/src/testdir/Makefile b/src/testdir/Makefile
index dc3dccb..7fa325f 100644
--- a/src/testdir/Makefile
+++ b/src/testdir/Makefile
@@ -14,7 +14,7 @@
 		test38.out test39.out test40.out test41.out test42.out \
 		test43.out test44.out test45.out test46.out test47.out \
 		test48.out test49.out test51.out test52.out test53.out \
-		test54.out test55.out test56.out test57.out
+		test54.out test55.out test56.out test57.out test58.out
 
 SCRIPTS_GUI = test16.out
 
@@ -46,7 +46,7 @@
 	-rm -rf X* viminfo
 
 .in.out:
-	-rm -f $*.failed test.ok X* viminfo
+	-rm -rf $*.failed test.ok X* viminfo
 	cp $*.ok test.ok
 	# Sleep a moment to avoid that the xterm title is messed up
 	@-sleep .2
@@ -58,7 +58,8 @@
 		  fi \
 		else echo $* NO OUTPUT >>test.log; \
 		fi"
-	-rm -rf X* test.ok viminfo
+	# Keep the files to make debugging easier.
+	# -rm -rf X* test.ok viminfo
 
 nolog:
 	-echo Test results: >test.log
diff --git a/src/testdir/test58.in b/src/testdir/test58.in
new file mode 100644
index 0000000..58275a3
--- /dev/null
+++ b/src/testdir/test58.in
@@ -0,0 +1,320 @@
+Tests for spell checking.     vim: set ft=vim :
+
+STARTTEST
+:so small.vim
+:"
+:" First generate a .spl file from a .dic and a .aff file.
+:set enc=latin1
+:/^affstart1/+1,/affend1/-1w Xtest.aff
+:/^dicstart/+1,/dicend/-1w Xtest.dic
+:mkspell Xtest Xtest
+:"
+:" use that spell file
+:set spl=Xtest.latin1.spl
+:set spell
+/^test1:
+]smm:let str = spellbadword()
+:$put =str
+`m:let lst = spellsuggest(str, 4)
+:$put =string(lst)
+`m]smm:let str = spellbadword()
+:$put =str
+`m:let lst = spellsuggest(str, 2)
+:$put =string(lst)
+`m]smm:let str = spellbadword()
+:$put =str
+`m:let lst = spellsuggest(str, 2)
+:$put =string(lst)
+`m]smm:let str = spellbadword()
+:$put =str
+`m:let lst = spellsuggest(str, 2)
+:$put =string(lst)
+`m]smm:let str = spellbadword()
+:$put =str
+`m:let lst = spellsuggest(str, 2)
+:$put =string(lst)
+`m]smm:let str = spellbadword()
+:$put =str
+`m:let lst = spellsuggest(str, 2)
+:$put =string(lst)
+:spelldump
+1GyG:q
+:$put
+:$put =soundfold('goobledygoook')
+:$put =soundfold('kóopërÿnôven')
+:$put =soundfold('oeverloos gezwets edale')
+:"
+:" and now with SAL instead of SOFO items; test automatic reloading
+gg:/^affstart2/+1,/^affend2/-1w! Xtest.aff
+:mkspell! Xtest Xtest
+:$put =soundfold('goobledygoook')
+:$put =soundfold('kóopërÿnôven')
+:$put =soundfold('oeverloos gezwets edale')
+:"
+:" also use an addition file
+gg:/^addstart/+1,/^addend/-1w! Xtest.latin1.add
+:mkspell! Xtest.latin1.add.spl Xtest.latin1.add
+:set spl=en
+:set spellfile=Xtest.latin1.add
+/^test2:
+]s:let str = spellbadword()
+:$put =str
+:set spl=en_us
+/^test2:
+]smm:let str = spellbadword()
+:$put =str
+`m]s:let str = spellbadword()
+:$put =str
+:set spl=en_gb
+/^test2:
+]smm:let str = spellbadword()
+:$put =str
+`m]s:let str = spellbadword()
+:$put =str
+:set spl=en_nz
+/^test2:
+]smm:let str = spellbadword()
+:$put =str
+`m]s:let str = spellbadword()
+:$put =str
+:set spl=en_ca
+/^test2:
+]smm:let str = spellbadword()
+:$put =str
+`m]s:let str = spellbadword()
+:$put =str
+:"
+gg:/^test output:/,$wq! test.out
+ENDTEST
+
+affstart1
+SET ISO8859-1
+TRY esianrtolcdugmphbyfvkwjkqxz-ëéèêïîäàâöüû'ESIANRTOLCDUGMPHBYFVKWJKQXZ
+
+FOL  àáâãäåæçèéêëìíîïðñòóôõöøùúûüýþßÿ
+LOW  àáâãäåæçèéêëìíîïðñòóôõöøùúûüýþßÿ
+UPP  ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖØÙÚÛÜÝÞßÿ
+
+SOFOFROM abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZàáâãäåæçèéêëìíîïðñòóôõöøùúûüýþßÿÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖØÙÚÛÜÝÞ¿
+SOFOTO   ebctefghejklnnepkrstevvkesebctefghejklnnepkrstevvkeseeeeeeeceeeeeeeedneeeeeeeeeeepseeeeeeeeceeeeeeeedneeeeeeeeeeep?
+
+MIDWORD	'-
+
+KEP =
+RAR ?
+BAD !
+
+NOSPLITSUGS
+
+PFX I N 1
+PFX I 0 in .
+
+PFX O Y 1
+PFX O 0 out .
+
+SFX S Y 2
+SFX S 0 s [^s]
+SFX S 0 es s
+
+REP 3
+REP g ch
+REP ch g
+REP svp s.v.p.
+
+MAP 9
+MAP aàáâãäå
+MAP eèéêë
+MAP iìíîï
+MAP oòóôõö
+MAP uùúûü
+MAP nñ
+MAP cç
+MAP yÿý
+MAP sß
+affend1
+
+affstart2
+SET ISO8859-1
+TRY esianrtolcdugmphbyfvkwjkqxz-ëéèêïîäàâöüû'ESIANRTOLCDUGMPHBYFVKWJKQXZ
+
+FOL  àáâãäåæçèéêëìíîïðñòóôõöøùúûüýþßÿ
+LOW  àáâãäåæçèéêëìíîïðñòóôõöøùúûüýþßÿ
+UPP  ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖØÙÚÛÜÝÞßÿ
+
+MIDWORD	'-
+
+KEP =
+RAR ?
+BAD !
+
+NOSPLITSUGS
+
+PFX I N 1
+PFX I 0 in .
+
+PFX O Y 1
+PFX O 0 out .
+
+SFX S Y 2
+SFX S 0 s [^s]
+SFX S 0 es s
+
+REP 3
+REP g ch
+REP ch g
+REP svp s.v.p.
+
+MAP 9
+MAP aàáâãäå
+MAP eèéêë
+MAP iìíîï
+MAP oòóôõö
+MAP uùúûü
+MAP nñ
+MAP cç
+MAP yÿý
+MAP sß
+
+SAL AH(AEIOUY)-^         *H
+SAL AR(AEIOUY)-^         *R
+SAL A(HR)^               *
+SAL A^                   *
+SAL AH(AEIOUY)-          H
+SAL AR(AEIOUY)-          R
+SAL A(HR)                _
+SAL À^                   *
+SAL Å^                   *
+SAL BB-                  _
+SAL B                    B
+SAL CQ-                  _
+SAL CIA                  X
+SAL CH                   X
+SAL C(EIY)-              S
+SAL CK                   K
+SAL COUGH^               KF
+SAL CC<                  C
+SAL C                    K
+SAL DG(EIY)              K
+SAL DD-                  _
+SAL D                    T
+SAL É<                   E
+SAL EH(AEIOUY)-^         *H
+SAL ER(AEIOUY)-^         *R
+SAL E(HR)^               *
+SAL ENOUGH^$             *NF
+SAL E^                   *
+SAL EH(AEIOUY)-          H
+SAL ER(AEIOUY)-          R
+SAL E(HR)                _
+SAL FF-                  _
+SAL F                    F
+SAL GN^                  N
+SAL GN$                  N
+SAL GNS$                 NS
+SAL GNED$                N
+SAL GH(AEIOUY)-          K
+SAL GH                   _
+SAL GG9                  K
+SAL G                    K
+SAL H                    H
+SAL IH(AEIOUY)-^         *H
+SAL IR(AEIOUY)-^         *R
+SAL I(HR)^               *
+SAL I^                   *
+SAL ING6                 N
+SAL IH(AEIOUY)-          H
+SAL IR(AEIOUY)-          R
+SAL I(HR)                _
+SAL J                    K
+SAL KN^                  N
+SAL KK-                  _
+SAL K                    K
+SAL LAUGH^               LF
+SAL LL-                  _
+SAL L                    L
+SAL MB$                  M
+SAL MM                   M
+SAL M                    M
+SAL NN-                  _
+SAL N                    N
+SAL OH(AEIOUY)-^         *H
+SAL OR(AEIOUY)-^         *R
+SAL O(HR)^               *
+SAL O^                   *
+SAL OH(AEIOUY)-          H
+SAL OR(AEIOUY)-          R
+SAL O(HR)                _
+SAL PH                   F
+SAL PN^                  N
+SAL PP-                  _
+SAL P                    P
+SAL Q                    K
+SAL RH^                  R
+SAL ROUGH^               RF
+SAL RR-                  _
+SAL R                    R
+SAL SCH(EOU)-            SK
+SAL SC(IEY)-             S
+SAL SH                   X
+SAL SI(AO)-              X
+SAL SS-                  _
+SAL S                    S
+SAL TI(AO)-              X
+SAL TH                   @
+SAL TCH--                _
+SAL TOUGH^               TF
+SAL TT-                  _
+SAL T                    T
+SAL UH(AEIOUY)-^         *H
+SAL UR(AEIOUY)-^         *R
+SAL U(HR)^               *
+SAL U^                   *
+SAL UH(AEIOUY)-          H
+SAL UR(AEIOUY)-          R
+SAL U(HR)                _
+SAL V^                   W
+SAL V                    F
+SAL WR^                  R
+SAL WH^                  W
+SAL W(AEIOU)-            W
+SAL X^                   S
+SAL X                    KS
+SAL Y(AEIOU)-            Y
+SAL ZZ-                  _
+SAL Z                    S
+affend2
+
+dicstart
+123456
+test
+# comment
+wrong
+Comment
+OK
+uk
+put/ISO
+the end
+deol
+déôr
+dicend
+
+addstart
+/regions=usgbnz
+elequint/2
+elekwint/3
+addend
+
+test1:
+inputs	wrong
+comment	wrong
+puts	OK
+ok	wrong
+Ok	wrong
+the end.  test wrong
+déôl
+
+test2:
+elequint test elekwint test elekwent asdf
+
+
+test output:
diff --git a/src/testdir/test58.ok b/src/testdir/test58.ok
new file mode 100644
index 0000000..6de8484
--- /dev/null
+++ b/src/testdir/test58.ok
@@ -0,0 +1,42 @@
+test output:
+inputs
+['input', 'puts', 'outputs', 'put']
+comment
+['Comment']
+ok
+['OK', 'uk']
+Ok
+['OK', 'Uk']
+test
+['test', 'Test']
+déôl
+['deol', 'déôr']
+# file: Xtest.latin1.spl
+Comment
+deol
+déôr
+input
+OK
+output
+outputs
+put
+puts
+test
+the end
+uk
+wrong
+gebletegek
+kepereneven
+everles gesvets etele
+kbltykk
+kprnfn
+*fls kswts tl
+elekwent
+elequint
+elekwint
+elekwint
+elekwent
+elequint
+elekwent
+elequint
+elekwint
diff --git a/src/version.h b/src/version.h
index e168db2..9656b5a 100644
--- a/src/version.h
+++ b/src/version.h
@@ -36,5 +36,5 @@
 #define VIM_VERSION_NODOT	"vim70aa"
 #define VIM_VERSION_SHORT	"7.0aa"
 #define VIM_VERSION_MEDIUM	"7.0aa ALPHA"
-#define VIM_VERSION_LONG	"VIM - Vi IMproved 7.0aa ALPHA (2005 Jul 3)"
-#define VIM_VERSION_LONG_DATE	"VIM - Vi IMproved 7.0aa ALPHA (2005 Jul 3, compiled "
+#define VIM_VERSION_LONG	"VIM - Vi IMproved 7.0aa ALPHA (2005 Jul 4)"
+#define VIM_VERSION_LONG_DATE	"VIM - Vi IMproved 7.0aa ALPHA (2005 Jul 4, compiled "