diff options
| author | Mattias Andrée <maandree@kth.se> | 2023-01-11 22:45:24 +0100 | 
|---|---|---|
| committer | Mattias Andrée <maandree@kth.se> | 2023-01-11 22:45:24 +0100 | 
| commit | 4fb270c05ff9a3f0e025c7964fc9444e76dcff2e (patch) | |
| tree | f554bd742b3324e0ef463367dedba71870df2ca5 | |
| parent | Add libfonts_get_font_root_dirs (diff) | |
| download | libfonts-4fb270c05ff9a3f0e025c7964fc9444e76dcff2e.tar.gz libfonts-4fb270c05ff9a3f0e025c7964fc9444e76dcff2e.tar.bz2 libfonts-4fb270c05ff9a3f0e025c7964fc9444e76dcff2e.tar.xz | |
Add alias file parsing function
Signed-off-by: Mattias Andrée <maandree@kth.se>
Diffstat (limited to '')
| -rw-r--r-- | Makefile | 1 | ||||
| -rw-r--r-- | libfonts.h | 32 | ||||
| -rw-r--r-- | libfonts_parse_alias_line.c | 119 | 
3 files changed, 152 insertions, 0 deletions
| @@ -29,6 +29,7 @@ PUBLIC_OBJ =\  	libfonts_get_output_dpi.o\  	libfonts_get_output_rendering_settings.o\  	libfonts_get_subpixel_order_class.o\ +	libfonts_parse_alias_line.o\  	libfonts_unget_subpixel_order_class.o\  	libfonts_used_environs.o @@ -12,6 +12,12 @@   */  #define LIBFONTS_CONTEXT_VERSION 0 +/** + * File name of file in font directories that is used + * to create font aliases + */ +#define LIBFONTS_ALIAS_FILE_NAME "fonts.alias" +  #if defined(__clang__)  # pragma clang diagnostic push @@ -1676,6 +1682,32 @@ extern const char *const libfonts_used_environs[];   */  int libfonts_get_font_root_dirs(char ***, size_t *, struct libfonts_context *); +/** + * Parse line from a font alias file + *  + * Font alias files are named "fonts.alias" (`LIBFONTS_ALIAS_FILE_NAME`) + * and are located in any font directory, i.e. directories returned by + * `libfonts_get_font_root_dirs` subdirectors (and further decedents) + *  + * @param   aliasp  Output parameter for the new alias + * @param   namep   Output parameter for the alias target, + *                  which can be ether a proper font name or an alias + * @param   line    The line to parse; parsing stops at the first + *                  newline or NUL byte + * @param   endp    Output parameter for the parsing end, i.e. the + *                  first newline or NUL byte in `line` + * @return          1 if the line included a font alias, + *                  0 if the line was blank or a comment line, + *                  -1 on failure + *  + * @throws  ENOMEM   Failed to allocate memory for `*aliasp` or `*namep` + * @throws  EBADMSG  The line is malformatted + *  + * `*aliasp` and `*namep` are set to `NULL` unless the function + * returns 1; `*endp` is updated even on failure + */ +int libfonts_parse_alias_line(char **, char **, const char *, char **); +  /* TODO add font listing */ diff --git a/libfonts_parse_alias_line.c b/libfonts_parse_alias_line.c new file mode 100644 index 0000000..844a400 --- /dev/null +++ b/libfonts_parse_alias_line.c @@ -0,0 +1,119 @@ +/* See LICENSE file for copyright and license details. */ +#include "common.h" +#ifndef TEST + + +int +libfonts_parse_alias_line(char **aliasp, char **namep, const char *line, char **endp) +{ +	const char *alias_start; +	const char *alias_end; +	const char *name_start; +	const char *name_end; +	int ret = 0; +	size_t len; + +	if (aliasp) +		*aliasp = NULL; +	if (namep) +		*namep = NULL; + +	while (isblank(*line)) +		line++; + +	if (!*line || *line == '!') +		goto out; + +	if (*line == '"') { +		alias_start = ++line; +		while (*line && *line != '\n' && *line != '"') +			line++; +		if (*line != '"') +			goto ebadmsg; +		alias_end = line++; +	} else { +		alias_start = line; +		while (*line && *line != '\n' && isblank(*line)) +			line++; +		alias_end = line; +	} + +	if (!isblank(*line)) +		goto ebadmsg; +	do { +		line++; +	} while (isblank(*line)); + +	if (*line == '"') { +		name_start = ++line; +		while (*line && *line != '\n' && *line != '"') +			line++; +		if (*line != '"') +			goto ebadmsg; +		name_end = line++; +	} else { +		name_start = line; +		while (*line && *line != '\n' && isblank(*line)) +			line++; +		name_end = line; +	} + +	while (isblank(*line)) +		line++; +	if (*line && *line != '\n') +		goto ebadmsg; + +	if (aliasp) { +		len = (size_t)(alias_end - alias_start); +		*aliasp = malloc(len + 1); +		if (!*aliasp) +			goto enomem; +		memcpy(*aliasp, alias_start, len); +		(*aliasp)[len] = '\0'; +	} + +	if (namep) { +		len = (size_t)(name_end - name_start); +		*namep = malloc(len + 1); +		if (!*namep) +			goto enomem; +		memcpy(*namep, name_start, len); +		(*namep)[len] = '\0'; +	} + +	*endp = *(char **)(void *)&line; +	return 1; + +ebadmsg: +	errno = EBADMSG; +	ret = -1; +out: +	while (*line && *line != '\n') +		line++; +out_at_end: +	if (endp) +		*endp = *(char **)(void *)&line; +	return ret; + +enomem: +	if (aliasp) { +		free(*aliasp); +		*aliasp = NULL; +	} +	errno = ENOMEM; +	ret = -1; +	goto out_at_end; +} + + +#else + + +int +main(void) +{ +	return 0; /* XXX add test */ +} + + +#endif | 
