Ignore:
Timestamp:
Sep 3, 2020, 3:52:14 PM (5 years ago)
Author:
bird
Message:

kash: refactoring evalcommand - complicated, part II.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/kash/parser.c

    r3065 r3437  
    11971197
    11981198parseredir: {
     1199        union node *np;
    11991200        char fd = *out;
    1200         union node *np;
     1201        char dummy[   sizeof(struct nfile) >= sizeof(struct ndup)
     1202                   && sizeof(struct nfile) >= sizeof(struct nhere) ? 1 : 0];
     1203        (void)dummy;
    12011204
    12021205        np = (union node *)stalloc(psh, sizeof (struct nfile));
     
    12181221                switch (c = pgetc(psh)) {
    12191222                case '<':
    1220                         if (sizeof (struct nfile) != sizeof (struct nhere)) {
    1221                                 np = (union node *)stalloc(psh, sizeof (struct nhere));
    1222                                 np->nfile.fd = 0;
    1223                         }
    12241223                        np->type = NHERE;
    12251224                        psh->heredoc = (struct heredoc *)stalloc(psh, sizeof (struct heredoc));
     
    14171416
    14181417                        case '\\':
    1419                                 if ((pc = pgetc(psh)) == '\n') {
     1418                                if ((pc = pgetc(psh)) == '\n') {
    14201419                                        psh->plinno++;
    14211420                                        if (psh->doprompt)
     
    14311430                                        continue;
    14321431                                }
    1433                                 if (pc != '\\' && pc != '`' && pc != '$'
    1434                                     && (!ISDBLQUOTE() || pc != '"'))
    1435                                         STPUTC(psh, '\\', pout);
     1432                                if (pc != '\\' && pc != '`' && pc != '$' && (!ISDBLQUOTE() || pc != '"'))
     1433                                        STPUTC(psh, '\\', pout);
    14361434                                break;
    14371435
     
    17791777        }
    17801778}
     1779
     1780/*
     1781 * Helper to copyparsetree.
     1782 */
     1783static struct nodelist *
     1784copynodelist(shinstance *psh, struct nodelist *src)
     1785{
     1786        struct nodelist *ret = NULL;
     1787        if (src) {
     1788                struct nodelist **ppnext = &ret;
     1789                while (src) {
     1790                        struct nodelist *dst = stalloc(psh, sizeof(*dst));
     1791                        dst->next = NULL;
     1792                        *ppnext = dst;
     1793                        ppnext = &dst->next;
     1794                        dst->n = copyparsetree(psh, src->n);
     1795                }
     1796        }
     1797        return ret;
     1798}
     1799
     1800/*
     1801 * Duplicates a node tree.
     1802 *
     1803 * Note! This could probably be generated from nodelist.
     1804 */
     1805union node *
     1806copyparsetree(shinstance *psh, union node *src)
     1807{
     1808        /** @todo Try avoid recursion for one of the sub-nodes, esp. when there
     1809         *        is a list like 'next' one. */
     1810        union node *ret;
     1811        if (src) {
     1812                int const type = src->type;
     1813                switch (type) {
     1814                        case NSEMI:
     1815                        case NAND:
     1816                        case NOR:
     1817                        case NWHILE:
     1818                        case NUNTIL:
     1819                                ret = (union node *)stalloc(psh, sizeof(src->nbinary));
     1820                                ret->nbinary.type = type;
     1821                                ret->nbinary.ch1  = copyparsetree(psh, src->nbinary.ch1);
     1822                                ret->nbinary.ch2  = copyparsetree(psh, src->nbinary.ch2);
     1823                                break;
     1824
     1825                        case NCMD:
     1826                                ret = (union node *)stalloc(psh, sizeof(src->ncmd));
     1827                                ret->ncmd.type     = NCMD;
     1828                                ret->ncmd.backgnd  = src->ncmd.backgnd;
     1829                                ret->ncmd.args     = copyparsetree(psh, src->ncmd.args);
     1830                                ret->ncmd.redirect = copyparsetree(psh, src->ncmd.redirect);
     1831                                break;
     1832
     1833                        case NPIPE:
     1834                                ret = (union node *)stalloc(psh, sizeof(src->npipe));
     1835                                ret->npipe.type     = NPIPE;
     1836                                ret->npipe.backgnd  = src->ncmd.backgnd;
     1837                                ret->npipe.cmdlist  = copynodelist(psh, src->npipe.cmdlist);
     1838                                break;
     1839
     1840                        case NREDIR:
     1841                        case NBACKGND:
     1842                        case NSUBSHELL:
     1843                                ret = (union node *)stalloc(psh, sizeof(src->nredir));
     1844                                ret->nredir.type     = type;
     1845                                ret->nredir.n        = copyparsetree(psh, src->nredir.n);
     1846                                ret->nredir.redirect = copyparsetree(psh, src->nredir.redirect);
     1847                                break;
     1848
     1849                        case NIF:
     1850                                ret = (union node *)stalloc(psh, sizeof(src->nif));
     1851                                ret->nif.type        = NIF;
     1852                                ret->nif.test        = copyparsetree(psh, src->nif.test);
     1853                                ret->nif.ifpart      = copyparsetree(psh, src->nif.ifpart);
     1854                                ret->nif.elsepart    = copyparsetree(psh, src->nif.elsepart);
     1855                                break;
     1856
     1857                        case NFOR:
     1858                                ret = (union node *)stalloc(psh, sizeof(src->nfor));
     1859                                ret->nfor.type       = NFOR;
     1860                                ret->nfor.args       = copyparsetree(psh, src->nfor.args);
     1861                                ret->nfor.body       = copyparsetree(psh, src->nfor.body);
     1862                                ret->nfor.var        = stsavestr(psh, src->nfor.var);
     1863                                break;
     1864
     1865                        case NCASE:
     1866                                ret = (union node *)stalloc(psh, sizeof(src->ncase));
     1867                                ret->ncase.type      = NCASE;
     1868                                ret->ncase.expr      = copyparsetree(psh, src->ncase.expr);
     1869                                ret->ncase.cases     = copyparsetree(psh, src->ncase.cases);
     1870                                break;
     1871
     1872                        case NCLIST:
     1873                                ret = (union node *)stalloc(psh, sizeof(src->nclist));
     1874                                ret->nclist.type     = NCLIST;
     1875                                ret->nclist.next     = copyparsetree(psh, src->nclist.next);
     1876                                ret->nclist.pattern  = copyparsetree(psh, src->nclist.pattern);
     1877                                ret->nclist.body     = copyparsetree(psh, src->nclist.body);
     1878                                break;
     1879
     1880                        case NDEFUN:
     1881                        case NARG:
     1882                                ret = (union node *)stalloc(psh, sizeof(src->narg));
     1883                                ret->narg.type       = type;
     1884                                ret->narg.next       = copyparsetree(psh, src->narg.next);
     1885                                ret->narg.text       = stsavestr(psh, src->narg.text);
     1886                                ret->narg.backquote  = copynodelist(psh, src->narg.backquote);
     1887                                break;
     1888
     1889                        case NTO:
     1890                        case NCLOBBER:
     1891                        case NFROM:
     1892                        case NFROMTO:
     1893                        case NAPPEND:
     1894                                ret = (union node *)stalloc(psh, sizeof(src->nfile));
     1895                                ret->nfile.type      = type;
     1896                                ret->nfile.fd        = src->nfile.fd;
     1897                                ret->nfile.next      = copyparsetree(psh, src->nfile.next);
     1898                                ret->nfile.fname     = copyparsetree(psh, src->nfile.fname);
     1899                                ret->nfile.expfname  = stsavestr(psh, src->nfile.expfname);
     1900                                break;
     1901
     1902                        case NTOFD:
     1903                        case NFROMFD:
     1904                                ret = (union node *)stalloc(psh, sizeof(src->ndup));
     1905                                ret->ndup.type       = type;
     1906                                ret->ndup.fd         = src->ndup.fd;
     1907                                ret->ndup.next       = copyparsetree(psh, src->ndup.next);
     1908                                ret->ndup.dupfd      = src->ndup.dupfd;
     1909                                ret->ndup.vname      = copyparsetree(psh, src->ndup.vname);
     1910                                break;
     1911
     1912                        case NHERE:
     1913                        case NXHERE:
     1914                                ret = (union node *)stalloc(psh, sizeof(src->nhere));
     1915                                ret->nhere.type      = type;
     1916                                ret->nhere.fd        = src->nhere.fd;
     1917                                ret->nhere.next      = copyparsetree(psh, src->nhere.next);
     1918                                ret->nhere.doc       = copyparsetree(psh, src->nhere.doc);
     1919                                break;
     1920
     1921                        case NNOT:
     1922                                ret = (union node *)stalloc(psh, sizeof(src->nnot));
     1923                                ret->nnot.type      = NNOT;
     1924                                ret->nnot.com       = copyparsetree(psh, src->nnot.com);
     1925                                break;
     1926
     1927                        default:
     1928                                error(psh, "Unknown node type: %d (node=%p)", src->type, src);
     1929                                return NULL;
     1930                }
     1931        } else {
     1932                ret = NULL;
     1933        }
     1934        return ret;
     1935}
     1936
Note: See TracChangeset for help on using the changeset viewer.