Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files. =================================================================== RCS file: /ftp/cvs/cvsroot/src/lib/libterminfo/term.c,v rcsdiff: /ftp/cvs/cvsroot/src/lib/libterminfo/term.c,v: warning: Unknown phrases like `commitid ...;' are present. retrieving revision 1.13.2.1 retrieving revision 1.21.2.1 diff -u -p -r1.13.2.1 -r1.21.2.1 --- src/lib/libterminfo/term.c 2012/10/30 18:59:18 1.13.2.1 +++ src/lib/libterminfo/term.c 2017/05/11 02:58:34 1.21.2.1 @@ -1,4 +1,4 @@ -/* $NetBSD: term.c,v 1.13.2.1 2012/10/30 18:59:18 yamt Exp $ */ +/* $NetBSD: term.c,v 1.21.2.1 2017/05/11 02:58:34 pgoyette Exp $ */ /* * Copyright (c) 2009, 2010, 2011 The NetBSD Foundation, Inc. @@ -28,7 +28,7 @@ */ #include -__RCSID("$NetBSD: term.c,v 1.13.2.1 2012/10/30 18:59:18 yamt Exp $"); +__RCSID("$NetBSD: term.c,v 1.21.2.1 2017/05/11 02:58:34 pgoyette Exp $"); #include @@ -54,34 +54,53 @@ const char *_ti_database; #include "compiled_terms.c" static int +allocset(void *pp, int init, size_t nelem, size_t elemsize) +{ + void **p = pp; + if (*p) { + memset(*p, init, nelem * elemsize); + return 0; + } + + if ((*p = calloc(nelem, elemsize)) == NULL) + return -1; + + if (init != 0) + memset(*p, init, nelem * elemsize); + return 0; +} + +static int _ti_readterm(TERMINAL *term, const char *cap, size_t caplen, int flags) { - uint8_t ver; + char ver; uint16_t ind, num; size_t len; TERMUSERDEF *ud; + if (caplen == 0) + goto out; ver = *cap++; + caplen--; /* Only read version 1 structures */ - if (ver != 1) { - errno = EINVAL; - return -1; - } + if (ver != 1) + goto out; - term->flags = calloc(TIFLAGMAX + 1, sizeof(char)); - if (term->flags == NULL) - return -1; - term->nums = malloc((TINUMMAX + 1) * sizeof(short)); - if (term->nums == NULL) + if (allocset(&term->flags, 0, TIFLAGMAX+1, sizeof(*term->flags)) == -1) return -1; - memset(term->nums, (short)-1, (TINUMMAX + 1) * sizeof(short)); - term->strs = calloc(TISTRMAX + 1, sizeof(char *)); - if (term->strs == NULL) + + if (allocset(&term->nums, -1, TINUMMAX+1, sizeof(*term->nums)) == -1) return -1; - term->_arealen = caplen; - term->_area = malloc(term->_arealen); - if (term->_area == NULL) + + if (allocset(&term->strs, 0, TISTRMAX+1, sizeof(*term->strs)) == -1) return -1; + + if (term->_arealen != caplen) { + term->_arealen = caplen; + term->_area = realloc(term->_area, term->_arealen); + if (term->_area == NULL) + return -1; + } memcpy(term->_area, cap, term->_arealen); cap = term->_area; @@ -119,7 +138,7 @@ _ti_readterm(TERMINAL *term, const char term->flags[ind] = 0; } } - + num = le16dec(cap); cap += sizeof(uint16_t); if (num != 0) { @@ -128,13 +147,13 @@ _ti_readterm(TERMINAL *term, const char for (; num != 0; num--) { ind = le16dec(cap); cap += sizeof(uint16_t); - term->nums[ind] = le16dec(cap); + term->nums[ind] = (short)le16dec(cap); if (flags == 0 && !VALID_NUMERIC(term->nums[ind])) term->nums[ind] = ABSENT_NUMERIC; cap += sizeof(uint16_t); } } - + num = le16dec(cap); cap += sizeof(uint16_t); if (num != 0) { @@ -154,13 +173,20 @@ _ti_readterm(TERMINAL *term, const char cap += len; } } - + num = le16dec(cap); cap += sizeof(uint16_t); if (num != 0) { - term->_nuserdefs = le16dec(cap); - term->_userdefs = malloc(sizeof(*term->_userdefs) * num); + num = le16dec(cap); cap += sizeof(uint16_t); + if (num != term->_nuserdefs) { + free(term->_userdefs); + term->_userdefs = NULL; + term->_nuserdefs = num; + } + if (allocset(&term->_userdefs, 0, term->_nuserdefs, + sizeof(*term->_userdefs)) == -1) + return -1; for (num = 0; num < term->_nuserdefs; num++) { ud = &term->_userdefs[num]; len = le16dec(cap); @@ -179,7 +205,7 @@ _ti_readterm(TERMINAL *term, const char break; case 'n': ud->flag = ABSENT_BOOLEAN; - ud->num = le16dec(cap); + ud->num = (short)le16dec(cap); if (flags == 0 && !VALID_NUMERIC(ud->num)) ud->num = ABSENT_NUMERIC; @@ -200,12 +226,21 @@ _ti_readterm(TERMINAL *term, const char cap += len; break; default: - errno = EINVAL; - return -1; + goto out; } } + } else { + term->_nuserdefs = 0; + if (term->_userdefs) { + free(term->_userdefs); + term->_userdefs = NULL; + } } + return 1; +out: + errno = EINVAL; + return -1; } static int @@ -243,7 +278,7 @@ _ti_dbgetterm(TERMINAL *term, const char data8 = data; if (data8[0] != 1) goto fail; - } else if (data8[0] != 1) + } else if (data8[0] != 1) goto fail; else if (klen + 3 >= len || le16dec(data8 + 1) != klen) goto fail; @@ -257,7 +292,7 @@ _ti_dbgetterm(TERMINAL *term, const char cdbr_close(db); return r; - fail: +fail: cdbr_close(db); return 0; } @@ -274,7 +309,7 @@ _ti_dbgettermp(TERMINAL *term, const cha do { for (p = path; *path != '\0' && *path != ':'; path++) continue; - l = path - p; + l = (size_t)(path - p); if (l != 0 && l + 1 < sizeof(pathbuf)) { memcpy(pathbuf, p, l); pathbuf[l] = '\0'; @@ -306,7 +341,7 @@ ticcmp(const TIC *tic, const char *name) if (s == NULL) l = strlen(alias); else - l = s - alias; + l = (size_t)(s - alias); if (len == l && memcmp(alias, name, l) == 0) return 0; if (s == NULL) @@ -332,9 +367,10 @@ _ti_findterm(TERMINAL *term, const char _ti_database = NULL; r = 0; - if ((e = getenv("TERMINFO")) != NULL && *e != '\0') + if ((e = getenv("TERMINFO")) != NULL && *e != '\0') { if (e[0] == '/') return _ti_dbgetterm(term, e, name, flags); + } c = NULL; if (e == NULL && (c = getenv("TERMCAP")) != NULL) { @@ -350,13 +386,13 @@ _ti_findterm(TERMINAL *term, const char if (e != NULL) { if (c == NULL) e = strdup(e); /* So we don't destroy env */ - if (e == NULL) + if (e == NULL) tic = NULL; - else + else { tic = _ti_compile(e, TIC_WARNING | TIC_ALIAS | TIC_DESCRIPTION | TIC_EXTRA); - if (c == NULL && e != NULL) free(e); + } if (tic != NULL && ticcmp(tic, name) == 0) { len = _ti_flatten(&f, tic); if (len != -1) { @@ -386,7 +422,6 @@ _ti_findterm(TERMINAL *term, const char r = _ti_dbgettermp(term, _PATH_TERMINFO, name, flags); return r; - } int