patch 9.0.1578: SpellCap highlight not always updated when needed

Problem:    SpellCap highlight not always updated when needed.
Solution:   Handle updating line below closed fold and other situations where
            only part of the window is redrawn. (Luuk van Baal, closes #12428,
            closes #12420)
diff --git a/src/spell.c b/src/spell.c
index 071ac9c..db70fcf 100644
--- a/src/spell.c
+++ b/src/spell.c
@@ -1342,7 +1342,7 @@
 	{
 	    // For spellbadword(): check if first word needs a capital.
 	    col = getwhitecols(line);
-	    if (check_need_cap(lnum, col))
+	    if (check_need_cap(curwin, lnum, col))
 		capcol = col;
 
 	    // Need to get the line again, may have looked at the previous
@@ -2815,24 +2815,20 @@
 
 /*
  * Check if the word at line "lnum" column "col" is required to start with a
- * capital.  This uses 'spellcapcheck' of the current buffer.
+ * capital.  This uses 'spellcapcheck' of the buffer in window "wp".
  */
     int
-check_need_cap(linenr_T lnum, colnr_T col)
+check_need_cap(win_T *wp, linenr_T lnum, colnr_T col)
 {
-    int		need_cap = FALSE;
-    char_u	*line;
-    char_u	*line_copy = NULL;
-    char_u	*p;
-    colnr_T	endcol;
-    regmatch_T	regmatch;
-
-    if (curwin->w_s->b_cap_prog == NULL)
+    if (wp->w_s->b_cap_prog == NULL)
 	return FALSE;
 
-    line = ml_get_curline();
-    endcol = 0;
-    if (getwhitecols(line) >= (int)col)
+    int		need_cap = FALSE;
+    char_u	*line = col ? ml_get_buf(wp->w_buffer, lnum, FALSE) : NULL;
+    char_u	*line_copy = NULL;
+    colnr_T	endcol = 0;
+
+    if (col == 0 || getwhitecols(line) >= col)
     {
 	// At start of line, check if previous line is empty or sentence
 	// ends there.
@@ -2840,13 +2836,16 @@
 	    need_cap = TRUE;
 	else
 	{
-	    line = ml_get(lnum - 1);
+	    line = ml_get_buf(wp->w_buffer, lnum - 1, FALSE);
 	    if (*skipwhite(line) == NUL)
 		need_cap = TRUE;
 	    else
 	    {
 		// Append a space in place of the line break.
 		line_copy = concat_str(line, (char_u *)" ");
+		if (line_copy == NULL)
+		    return FALSE;
+
 		line = line_copy;
 		endcol = (colnr_T)STRLEN(line);
 	    }
@@ -2858,13 +2857,14 @@
     if (endcol > 0)
     {
 	// Check if sentence ends before the bad word.
-	regmatch.regprog = curwin->w_s->b_cap_prog;
+	regmatch_T	regmatch;
+	regmatch.regprog = wp->w_s->b_cap_prog;
 	regmatch.rm_ic = FALSE;
-	p = line + endcol;
+	char_u *p = line + endcol;
 	for (;;)
 	{
 	    MB_PTR_BACK(line, p);
-	    if (p == line || spell_iswordp_nmw(p, curwin))
+	    if (p == line || spell_iswordp_nmw(p, wp))
 		break;
 	    if (vim_regexec(&regmatch, p, 0)
 					 && regmatch.endp[0] == line + endcol)
@@ -2873,7 +2873,7 @@
 		break;
 	    }
 	}
-	curwin->w_s->b_cap_prog = regmatch.regprog;
+	wp->w_s->b_cap_prog = regmatch.regprog;
     }
 
     vim_free(line_copy);
@@ -4340,7 +4340,7 @@
     void
 spell_expand_check_cap(colnr_T col)
 {
-    spell_expand_need_cap = check_need_cap(curwin->w_cursor.lnum, col);
+    spell_expand_need_cap = check_need_cap(curwin, curwin->w_cursor.lnum, col);
 }
 
 /*