aboutsummaryrefslogtreecommitdiffstats
path: root/contrib/tools/python3/src/Objects/stringlib/localeutil.h
blob: de48a62f1f47d39cc85c64ac0661ac149def5978 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
/* _PyUnicode_InsertThousandsGrouping() helper functions */ 
 
typedef struct { 
    const char *grouping; 
    char previous; 
    Py_ssize_t i; /* Where we're currently pointing in grouping. */ 
} GroupGenerator; 
 
 
static void 
GroupGenerator_init(GroupGenerator *self, const char *grouping) 
{ 
    self->grouping = grouping; 
    self->i = 0; 
    self->previous = 0; 
} 
 
 
/* Returns the next grouping, or 0 to signify end. */ 
static Py_ssize_t 
GroupGenerator_next(GroupGenerator *self) 
{ 
    /* Note that we don't really do much error checking here. If a 
       grouping string contains just CHAR_MAX, for example, then just 
       terminate the generator. That shouldn't happen, but at least we 
       fail gracefully. */ 
    switch (self->grouping[self->i]) { 
    case 0: 
        return self->previous; 
    case CHAR_MAX: 
        /* Stop the generator. */ 
        return 0; 
    default: { 
        char ch = self->grouping[self->i]; 
        self->previous = ch; 
        self->i++; 
        return (Py_ssize_t)ch; 
    } 
    } 
} 
 
 
/* Fill in some digits, leading zeros, and thousands separator. All 
   are optional, depending on when we're called. */ 
static void 
InsertThousandsGrouping_fill(_PyUnicodeWriter *writer, Py_ssize_t *buffer_pos, 
                             PyObject *digits, Py_ssize_t *digits_pos, 
                             Py_ssize_t n_chars, Py_ssize_t n_zeros, 
                             PyObject *thousands_sep, Py_ssize_t thousands_sep_len, 
                             Py_UCS4 *maxchar) 
{ 
    if (!writer) { 
        /* if maxchar > 127, maxchar is already set */ 
        if (*maxchar == 127 && thousands_sep) { 
            Py_UCS4 maxchar2 = PyUnicode_MAX_CHAR_VALUE(thousands_sep); 
            *maxchar = Py_MAX(*maxchar, maxchar2); 
        } 
        return; 
    } 
 
    if (thousands_sep) { 
        *buffer_pos -= thousands_sep_len; 
 
        /* Copy the thousands_sep chars into the buffer. */ 
        _PyUnicode_FastCopyCharacters(writer->buffer, *buffer_pos, 
                                      thousands_sep, 0, 
                                      thousands_sep_len); 
    } 
 
    *buffer_pos -= n_chars; 
    *digits_pos -= n_chars; 
    _PyUnicode_FastCopyCharacters(writer->buffer, *buffer_pos, 
                                  digits, *digits_pos, 
                                  n_chars); 
 
    if (n_zeros) { 
        *buffer_pos -= n_zeros; 
        enum PyUnicode_Kind kind = PyUnicode_KIND(writer->buffer); 
        void *data = PyUnicode_DATA(writer->buffer); 
        unicode_fill(kind, data, '0', *buffer_pos, n_zeros);
    } 
}