summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorEli Zaretskii <eliz@gnu.org>2014-10-03 19:33:07 +0300
committerEli Zaretskii <eliz@gnu.org>2014-10-03 19:33:07 +0300
commit6382f0a1d64caa4a688b6a264a4693ffe93c63ca (patch)
tree19a580012583a6de610e086af3b3f4caee78bf42 /src
parente8207eb00d5be19c9e3678cc9697504da60b68c5 (diff)
downloademacs-6382f0a1d64caa4a688b6a264a4693ffe93c63ca.tar.gz
Fixed handling of LRI, RLI, and FSI.
Scrolled successfully through the entire biditest.txt file. The parentheses are still not implemented.
Diffstat (limited to 'src')
-rw-r--r--src/bidi.c305
1 files changed, 157 insertions, 148 deletions
diff --git a/src/bidi.c b/src/bidi.c
index 1cceccf0119..aad867887b1 100644
--- a/src/bidi.c
+++ b/src/bidi.c
@@ -1726,6 +1726,8 @@ bidi_resolve_explicit (struct bidi_it *bidi_it)
{
eassert (bidi_it->prev.charpos == bidi_it->charpos - 1);
prev_type = bidi_it->prev.orig_type;
+ if (prev_type == FSI)
+ prev_type = bidi_it->type_after_w1;
}
}
/* Don't move at end of buffer/string. */
@@ -1740,6 +1742,8 @@ bidi_resolve_explicit (struct bidi_it *bidi_it)
emacs_abort ();
bidi_it->bytepos += bidi_it->ch_len;
prev_type = bidi_it->orig_type;
+ if (prev_type == FSI)
+ prev_type = bidi_it->type_after_w1;
}
else /* EOB or end of string */
prev_type = NEUTRAL_B;
@@ -1763,78 +1767,48 @@ bidi_resolve_explicit (struct bidi_it *bidi_it)
embedding level of the _following_ characters, so we must
first look at the type of the previous character to support
that. */
- switch (prev_type)
- {
- case FSI: /* X5c */
- end = string_p ? bidi_it->string.schars : ZV;
- disp_pos = bidi_it->disp_pos;
- disp_prop = bidi_it->disp_prop;
- nchars = bidi_it->nchars;
- ch_len = bidi_it->ch_len;
- typ1 = find_first_strong_char (bidi_it->charpos,
- bidi_it->bytepos, end,
- &disp_pos, &disp_prop,
- &bidi_it->string, bidi_it->w,
- string_p, bidi_it->frame_window_p,
- &ch_len, &nchars, true);
- if (typ1 != STRONG_R && typ1 != STRONG_AL)
- {
- type = LRI;
- goto fsi_as_lri;
- }
- else
- type = RLI;
- /* FALLTHROUGH */
- case RLI: /* X5a */
- if (override == NEUTRAL_DIR)
- bidi_it->type_after_w1 = type;
- else /* Unicode 8.0 correction. */
- bidi_it->type_after_w1 = (override == L2R ? STRONG_L : STRONG_R);
- bidi_check_type (bidi_it->type_after_w1);
- if (current_level < BIDI_MAXDEPTH
- && bidi_it->invalid_levels == 0
- && bidi_it->invalid_isolates == 0)
- {
- new_level = ((current_level + 1) & ~1) + 1;
- bidi_it->isolate_level++;
- bidi_push_embedding_level (bidi_it, new_level,
- NEUTRAL_DIR, true);
- }
- else
- bidi_it->invalid_isolates++;
- break;
- case LRI: /* X5b */
- fsi_as_lri:
- if (override == NEUTRAL_DIR)
- bidi_it->type_after_w1 = type;
- else /* Unicode 8.0 correction. */
- bidi_it->type_after_w1 = (override == L2R ? STRONG_L : STRONG_R);
- bidi_check_type (bidi_it->type_after_w1);
- if (current_level < BIDI_MAXDEPTH - 1
- && bidi_it->invalid_levels == 0
- && bidi_it->invalid_isolates == 0)
- {
- new_level = ((current_level + 2) & ~1);
- bidi_it->isolate_level++;
- bidi_push_embedding_level (bidi_it, new_level,
- NEUTRAL_DIR, true);
- }
- else
- bidi_it->invalid_isolates++;
- break;
- case PDF: /* X7 */
- if (!bidi_it->invalid_isolates)
- {
- if (bidi_it->invalid_levels)
- bidi_it->invalid_levels--;
- else if (!isolate_status && bidi_it->stack_idx >= 1)
- new_level = bidi_pop_embedding_level (bidi_it);
- }
- break;
- default:
- /* Nothing. */
- break;
- }
+ switch (prev_type)
+ {
+ case RLI: /* X5a */
+ if (current_level < BIDI_MAXDEPTH
+ && bidi_it->invalid_levels == 0
+ && bidi_it->invalid_isolates == 0)
+ {
+ new_level = ((current_level + 1) & ~1) + 1;
+ bidi_it->isolate_level++;
+ bidi_push_embedding_level (bidi_it, new_level,
+ NEUTRAL_DIR, true);
+ }
+ else
+ bidi_it->invalid_isolates++;
+ break;
+ case LRI: /* X5b */
+ if (current_level < BIDI_MAXDEPTH - 1
+ && bidi_it->invalid_levels == 0
+ && bidi_it->invalid_isolates == 0)
+ {
+ new_level = ((current_level + 2) & ~1);
+ bidi_it->isolate_level++;
+ bidi_push_embedding_level (bidi_it, new_level,
+ NEUTRAL_DIR, true);
+ }
+ else
+ bidi_it->invalid_isolates++;
+ break;
+ case PDF: /* X7 */
+ if (!bidi_it->invalid_isolates)
+ {
+ if (bidi_it->invalid_levels)
+ bidi_it->invalid_levels--;
+ else if (!isolate_status && bidi_it->stack_idx >= 1)
+ new_level = bidi_pop_embedding_level (bidi_it);
+ }
+ break;
+ default:
+ eassert (prev_type != FSI);
+ /* Nothing. */
+ break;
+ }
/* Fetch the character at BYTEPOS. If it is covered by a
display string, treat the entire run of covered characters as
a single character u+FFFC. */
@@ -1859,85 +1833,120 @@ bidi_resolve_explicit (struct bidi_it *bidi_it)
switch (type)
{
- case RLE: /* X2 */
- case RLO: /* X4 */
+ case RLE: /* X2 */
+ case RLO: /* X4 */
+ bidi_it->type_after_w1 = type;
+ bidi_check_type (bidi_it->type_after_w1);
+ type = WEAK_BN; /* X9/Retaining */
+ if (new_level < BIDI_MAXDEPTH
+ && bidi_it->invalid_levels == 0
+ && bidi_it->invalid_isolates == 0)
+ {
+ /* Compute the least odd embedding level greater than
+ the current level. */
+ new_level = ((new_level + 1) & ~1) + 1;
+ if (bidi_it->type_after_w1 == RLE)
+ override = NEUTRAL_DIR;
+ else
+ override = R2L;
+ bidi_push_embedding_level (bidi_it, new_level, override, false);
+ bidi_it->resolved_level = new_level;
+ }
+ else
+ {
+ if (bidi_it->invalid_isolates == 0)
+ bidi_it->invalid_levels++;
+ }
+ break;
+ case LRE: /* X3 */
+ case LRO: /* X5 */
+ bidi_it->type_after_w1 = type;
+ bidi_check_type (bidi_it->type_after_w1);
+ type = WEAK_BN; /* X9/Retaining */
+ if (new_level < BIDI_MAXDEPTH - 1
+ && bidi_it->invalid_levels == 0
+ && bidi_it->invalid_isolates == 0)
+ {
+ /* Compute the least even embedding level greater than
+ the current level. */
+ new_level = ((new_level + 2) & ~1);
+ if (bidi_it->type_after_w1 == LRE)
+ override = NEUTRAL_DIR;
+ else
+ override = L2R;
+ bidi_push_embedding_level (bidi_it, new_level, override, false);
+ bidi_it->resolved_level = new_level;
+ }
+ else
+ {
+ if (bidi_it->invalid_isolates == 0)
+ bidi_it->invalid_levels++;
+ }
+ break;
+ case FSI: /* X5c */
+ end = string_p ? bidi_it->string.schars : ZV;
+ disp_pos = bidi_it->disp_pos;
+ disp_prop = bidi_it->disp_prop;
+ nchars = bidi_it->nchars;
+ ch_len = bidi_it->ch_len;
+ typ1 = find_first_strong_char (bidi_it->charpos,
+ bidi_it->bytepos, end,
+ &disp_pos, &disp_prop,
+ &bidi_it->string, bidi_it->w,
+ string_p, bidi_it->frame_window_p,
+ &ch_len, &nchars, true);
+ if (typ1 != STRONG_R && typ1 != STRONG_AL)
+ {
+ type = LRI;
+ goto fsi_as_lri;
+ }
+ else
+ type = RLI;
+ /* FALLTHROUGH */
+ case RLI: /* X5a */
+ if (override == NEUTRAL_DIR)
bidi_it->type_after_w1 = type;
- bidi_check_type (bidi_it->type_after_w1);
- type = WEAK_BN; /* X9/Retaining */
- if (new_level < BIDI_MAXDEPTH
- && bidi_it->invalid_levels == 0
- && bidi_it->invalid_isolates == 0)
- {
- /* Compute the least odd embedding level greater than
- the current level. */
- new_level = ((new_level + 1) & ~1) + 1;
- if (bidi_it->type_after_w1 == RLE)
- override = NEUTRAL_DIR;
- else
- override = R2L;
- bidi_push_embedding_level (bidi_it, new_level, override, false);
- bidi_it->resolved_level = new_level;
- }
- else
- {
- if (bidi_it->invalid_isolates == 0)
- bidi_it->invalid_levels++;
- }
- break;
- case LRE: /* X3 */
- case LRO: /* X5 */
+ else /* Unicode 8.0 correction. */
+ bidi_it->type_after_w1 = (override == L2R ? STRONG_L : STRONG_R);
+ bidi_check_type (bidi_it->type_after_w1);
+ break;
+ case LRI: /* X5b */
+ fsi_as_lri:
+ if (override == NEUTRAL_DIR)
bidi_it->type_after_w1 = type;
- bidi_check_type (bidi_it->type_after_w1);
- type = WEAK_BN; /* X9/Retaining */
- if (new_level < BIDI_MAXDEPTH - 1
- && bidi_it->invalid_levels == 0
- && bidi_it->invalid_isolates == 0)
- {
- /* Compute the least even embedding level greater than
- the current level. */
- new_level = ((new_level + 2) & ~1);
- if (bidi_it->type_after_w1 == LRE)
- override = NEUTRAL_DIR;
- else
- override = L2R;
- bidi_push_embedding_level (bidi_it, new_level, override, false);
- bidi_it->resolved_level = new_level;
- }
- else
- {
- if (bidi_it->invalid_isolates == 0)
- bidi_it->invalid_levels++;
- }
- break;
- case PDI: /* X6a */
- if (bidi_it->invalid_isolates)
- bidi_it->invalid_isolates--;
- else if (bidi_it->isolate_level > 0)
- {
- bidi_it->invalid_levels = 0;
- while (!bidi_it->level_stack[bidi_it->stack_idx].isolate_status)
- bidi_pop_embedding_level (bidi_it);
- eassert (bidi_it->stack_idx > 0);
- new_level = bidi_pop_embedding_level (bidi_it);
- bidi_it->isolate_level--;
- }
- bidi_it->resolved_level = new_level;
- /* Unicode 8.0 correction. */
- if (bidi_it->level_stack[bidi_it->stack_idx].override == L2R)
- bidi_it->type_after_w1 = STRONG_L;
- else if (bidi_it->level_stack[bidi_it->stack_idx].override == R2L)
- bidi_it->type_after_w1 = STRONG_R;
- else
- bidi_it->type_after_w1 = type;
- break;
- case PDF: /* X7 */
+ else /* Unicode 8.0 correction. */
+ bidi_it->type_after_w1 = (override == L2R ? STRONG_L : STRONG_R);
+ bidi_check_type (bidi_it->type_after_w1);
+ break;
+ case PDI: /* X6a */
+ if (bidi_it->invalid_isolates)
+ bidi_it->invalid_isolates--;
+ else if (bidi_it->isolate_level > 0)
+ {
+ bidi_it->invalid_levels = 0;
+ while (!bidi_it->level_stack[bidi_it->stack_idx].isolate_status)
+ bidi_pop_embedding_level (bidi_it);
+ eassert (bidi_it->stack_idx > 0);
+ new_level = bidi_pop_embedding_level (bidi_it);
+ bidi_it->isolate_level--;
+ }
+ bidi_it->resolved_level = new_level;
+ /* Unicode 8.0 correction. */
+ if (bidi_it->level_stack[bidi_it->stack_idx].override == L2R)
+ bidi_it->type_after_w1 = STRONG_L;
+ else if (bidi_it->level_stack[bidi_it->stack_idx].override == R2L)
+ bidi_it->type_after_w1 = STRONG_R;
+ else
bidi_it->type_after_w1 = type;
- bidi_check_type (bidi_it->type_after_w1);
- type = WEAK_BN; /* X9/Retaining */
- break;
- default:
- /* Nothing. */
- break;
+ break;
+ case PDF: /* X7 */
+ bidi_it->type_after_w1 = type;
+ bidi_check_type (bidi_it->type_after_w1);
+ type = WEAK_BN; /* X9/Retaining */
+ break;
+ default:
+ /* Nothing. */
+ break;
}
bidi_it->type = type;