1*ce7279d8Sjsg /* $OpenBSD: rcs.h,v 1.19 2024/05/21 05:00:48 jsg Exp $ */ 22dc36bedSjoris /* 32dc36bedSjoris * Copyright (c) 2004 Jean-Francois Brousseau <jfb@openbsd.org> 42dc36bedSjoris * All rights reserved. 52dc36bedSjoris * 62dc36bedSjoris * Redistribution and use in source and binary forms, with or without 72dc36bedSjoris * modification, are permitted provided that the following conditions 82dc36bedSjoris * are met: 92dc36bedSjoris * 102dc36bedSjoris * 1. Redistributions of source code must retain the above copyright 112dc36bedSjoris * notice, this list of conditions and the following disclaimer. 122dc36bedSjoris * 2. The name of the author may not be used to endorse or promote products 132dc36bedSjoris * derived from this software without specific prior written permission. 142dc36bedSjoris * 152dc36bedSjoris * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, 162dc36bedSjoris * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY 172dc36bedSjoris * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL 182dc36bedSjoris * THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 192dc36bedSjoris * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 202dc36bedSjoris * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; 212dc36bedSjoris * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 222dc36bedSjoris * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 232dc36bedSjoris * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF 242dc36bedSjoris * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 252dc36bedSjoris */ 262dc36bedSjoris 272dc36bedSjoris #ifndef RCS_H 282dc36bedSjoris #define RCS_H 292dc36bedSjoris 304781e2faSxsa #include <sys/queue.h> 314781e2faSxsa 32394437e6Stobias #include <stdio.h> 33394437e6Stobias 342dc36bedSjoris #include "buf.h" 352dc36bedSjoris 362dc36bedSjoris #define RCS_DIFF_MAXARG 32 372dc36bedSjoris #define RCS_DIFF_DIV \ 382dc36bedSjoris "===================================================================" 392dc36bedSjoris 402dc36bedSjoris #define RCSDIR "RCS" 412dc36bedSjoris #define RCS_FILE_EXT ",v" 422dc36bedSjoris 432dc36bedSjoris #define RCS_HEAD_BRANCH "HEAD" 442dc36bedSjoris #define RCS_HEAD_INIT "1.1" 452dc36bedSjoris #define RCS_HEAD_REV ((RCSNUM *)(-1)) 462dc36bedSjoris 472dc36bedSjoris 48b7f54172Stobias #define RCS_STATE_INVALCHAR "$,:;@" 492dc36bedSjoris #define RCS_SYM_INVALCHAR "$,.:;@" 502dc36bedSjoris 512dc36bedSjoris #define RCS_MAGIC_BRANCH ".0." 522dc36bedSjoris #define RCS_STATE_EXP "Exp" 532dc36bedSjoris #define RCS_STATE_DEAD "dead" 542dc36bedSjoris 552dc36bedSjoris /* lock types */ 562dc36bedSjoris #define RCS_LOCK_INVAL (-1) 572dc36bedSjoris #define RCS_LOCK_LOOSE 0 582dc36bedSjoris #define RCS_LOCK_STRICT 1 592dc36bedSjoris 602dc36bedSjoris /* 612dc36bedSjoris * Keyword expansion table 622dc36bedSjoris */ 632dc36bedSjoris #define RCS_KW_AUTHOR 0x1000 642dc36bedSjoris #define RCS_KW_DATE 0x2000 652dc36bedSjoris #define RCS_KW_LOG 0x4000 662dc36bedSjoris #define RCS_KW_NAME 0x8000 672dc36bedSjoris #define RCS_KW_RCSFILE 0x0100 682dc36bedSjoris #define RCS_KW_REVISION 0x0200 692dc36bedSjoris #define RCS_KW_SOURCE 0x0400 702dc36bedSjoris #define RCS_KW_STATE 0x0800 712dc36bedSjoris #define RCS_KW_FULLPATH 0x0010 72b5a78d44Sschwarze #define RCS_KW_MDOCDATE 0x0020 73ef21cefbSnicm #define RCS_KW_LOCKER 0x10000 742dc36bedSjoris 752dc36bedSjoris #define RCS_KW_ID \ 762dc36bedSjoris (RCS_KW_RCSFILE | RCS_KW_REVISION | RCS_KW_DATE \ 77ef21cefbSnicm | RCS_KW_AUTHOR | RCS_KW_STATE | RCS_KW_LOCKER) 782dc36bedSjoris 792dc36bedSjoris #define RCS_KW_HEADER (RCS_KW_ID | RCS_KW_FULLPATH) 802dc36bedSjoris 812dc36bedSjoris /* RCS keyword expansion modes (kflags) */ 822dc36bedSjoris #define RCS_KWEXP_NONE 0x00 832dc36bedSjoris #define RCS_KWEXP_NAME 0x01 /* include keyword name */ 842dc36bedSjoris #define RCS_KWEXP_VAL 0x02 /* include keyword value */ 852dc36bedSjoris #define RCS_KWEXP_LKR 0x04 /* include name of locker */ 862dc36bedSjoris #define RCS_KWEXP_OLD 0x08 /* generate old keyword string */ 872dc36bedSjoris #define RCS_KWEXP_ERR 0x10 /* mode has an error */ 882dc36bedSjoris 892dc36bedSjoris #define RCS_KWEXP_DEFAULT (RCS_KWEXP_NAME | RCS_KWEXP_VAL) 902dc36bedSjoris #define RCS_KWEXP_KVL (RCS_KWEXP_NAME | RCS_KWEXP_VAL | RCS_KWEXP_LKR) 912dc36bedSjoris 922dc36bedSjoris #define RCS_KWEXP_INVAL(k) \ 932dc36bedSjoris ((k & RCS_KWEXP_ERR) || \ 942dc36bedSjoris ((k & RCS_KWEXP_OLD) && (k & ~RCS_KWEXP_OLD))) 952dc36bedSjoris 962dc36bedSjoris struct rcs_kw { 972dc36bedSjoris char kw_str[16]; 982dc36bedSjoris int kw_type; 992dc36bedSjoris }; 1002dc36bedSjoris 1012dc36bedSjoris #define RCS_NKWORDS (sizeof(rcs_expkw)/sizeof(rcs_expkw[0])) 1022dc36bedSjoris 1032dc36bedSjoris #define RCSNUM_MAXNUM USHRT_MAX 1042dc36bedSjoris #define RCSNUM_MAXLEN 64 1052dc36bedSjoris 1062dc36bedSjoris #define RCSNUM_ISBRANCH(n) ((n)->rn_len % 2) 1072dc36bedSjoris #define RCSNUM_ISBRANCHREV(n) (!((n)->rn_len % 2) && ((n)->rn_len >= 4)) 1082dc36bedSjoris #define RCSNUM_NO_MAGIC (1<<0) 1092dc36bedSjoris 1102dc36bedSjoris /* file flags */ 1112dc36bedSjoris #define RCS_READ (1<<0) 1122dc36bedSjoris #define RCS_WRITE (1<<1) 1132dc36bedSjoris #define RCS_RDWR (RCS_READ|RCS_WRITE) 1142dc36bedSjoris #define RCS_CREATE (1<<2) /* create the file */ 1152dc36bedSjoris #define RCS_PARSE_FULLY (1<<3) /* fully parse it on open */ 1162dc36bedSjoris 1172dc36bedSjoris /* internal flags */ 1182dc36bedSjoris #define RCS_PARSED (1<<4) /* file has been parsed */ 1192dc36bedSjoris #define RCS_SYNCED (1<<5) /* in-mem copy is sync with disk copy */ 1202dc36bedSjoris #define RCS_SLOCK (1<<6) /* strict lock */ 1212dc36bedSjoris 1222dc36bedSjoris /* parser flags */ 1232dc36bedSjoris #define PARSED_DELTAS (1<<7) /* all deltas are parsed */ 1242dc36bedSjoris #define PARSED_DESC (1<<8) /* the description is parsed */ 1252dc36bedSjoris #define PARSED_DELTATEXTS (1<<9) /* all delta texts are parsed */ 1262dc36bedSjoris 1272dc36bedSjoris /* delta flags */ 1282dc36bedSjoris #define RCS_RD_DEAD 0x01 /* dead */ 1292dc36bedSjoris #define RCS_RD_SELECT 0x02 /* select for operation */ 1302dc36bedSjoris 1312dc36bedSjoris /* RCS error codes */ 1322dc36bedSjoris #define RCS_ERR_NOERR 0 1332dc36bedSjoris #define RCS_ERR_NOENT 1 1342dc36bedSjoris #define RCS_ERR_DUPENT 2 1352dc36bedSjoris #define RCS_ERR_BADNUM 3 1362dc36bedSjoris #define RCS_ERR_BADSYM 4 1372dc36bedSjoris #define RCS_ERR_PARSE 5 1382dc36bedSjoris #define RCS_ERR_ERRNO 255 1392dc36bedSjoris 1402dc36bedSjoris /* used for rcs_checkout_rev */ 1412dc36bedSjoris #define CHECKOUT_REV_CREATED 1 1422dc36bedSjoris #define CHECKOUT_REV_MERGED 2 1432dc36bedSjoris #define CHECKOUT_REV_REMOVED 3 1442dc36bedSjoris #define CHECKOUT_REV_UPDATED 4 1452dc36bedSjoris 14652248372Sjcs /* commitids in cvs/cvsnt can be up to 64 bytes */ 14752248372Sjcs #define RCS_COMMITID_MAXLEN 64 14852248372Sjcs 1492dc36bedSjoris typedef struct rcs_num { 1502dc36bedSjoris u_int rn_len; 1512dc36bedSjoris u_int16_t *rn_id; 1522dc36bedSjoris } RCSNUM; 1532dc36bedSjoris 1542dc36bedSjoris struct rcs_access { 1552dc36bedSjoris char *ra_name; 1562dc36bedSjoris TAILQ_ENTRY(rcs_access) ra_list; 1572dc36bedSjoris }; 1582dc36bedSjoris 1592dc36bedSjoris struct rcs_sym { 1602dc36bedSjoris char *rs_name; 1612dc36bedSjoris RCSNUM *rs_num; 1622dc36bedSjoris TAILQ_ENTRY(rcs_sym) rs_list; 1632dc36bedSjoris }; 1642dc36bedSjoris 1652dc36bedSjoris struct rcs_lock { 1662dc36bedSjoris char *rl_name; 1672dc36bedSjoris RCSNUM *rl_num; 1682dc36bedSjoris 1692dc36bedSjoris TAILQ_ENTRY(rcs_lock) rl_list; 1702dc36bedSjoris }; 1712dc36bedSjoris 1722dc36bedSjoris struct rcs_branch { 1732dc36bedSjoris RCSNUM *rb_num; 1742dc36bedSjoris TAILQ_ENTRY(rcs_branch) rb_list; 1752dc36bedSjoris }; 1762dc36bedSjoris 1772dc36bedSjoris TAILQ_HEAD(rcs_dlist, rcs_delta); 1782dc36bedSjoris 1792dc36bedSjoris struct rcs_delta { 1802dc36bedSjoris RCSNUM *rd_num; 1812dc36bedSjoris RCSNUM *rd_next; 1822dc36bedSjoris u_int rd_flags; 1832dc36bedSjoris struct tm rd_date; 1842dc36bedSjoris char *rd_author; 1852dc36bedSjoris char *rd_state; 18652248372Sjcs char *rd_commitid; 1872dc36bedSjoris char *rd_log; 1882dc36bedSjoris char *rd_locker; 1892dc36bedSjoris u_char *rd_text; 1902dc36bedSjoris size_t rd_tlen; 1912dc36bedSjoris 1922dc36bedSjoris TAILQ_HEAD(, rcs_branch) rd_branches; 1932dc36bedSjoris TAILQ_ENTRY(rcs_delta) rd_list; 1942dc36bedSjoris }; 1952dc36bedSjoris 1962dc36bedSjoris 1972dc36bedSjoris typedef struct rcs_file { 198394437e6Stobias FILE *rf_file; 1992dc36bedSjoris char *rf_path; 2002dc36bedSjoris mode_t rf_mode; 2012dc36bedSjoris u_int rf_flags; 2022dc36bedSjoris 2032dc36bedSjoris RCSNUM *rf_head; 2042dc36bedSjoris RCSNUM *rf_branch; 2052dc36bedSjoris char *rf_comment; 2062dc36bedSjoris char *rf_expand; 2072dc36bedSjoris char *rf_desc; 2082dc36bedSjoris 2092dc36bedSjoris u_int rf_ndelta; 2102dc36bedSjoris struct rcs_dlist rf_delta; 2112dc36bedSjoris TAILQ_HEAD(rcs_alist, rcs_access) rf_access; 2122dc36bedSjoris TAILQ_HEAD(rcs_slist, rcs_sym) rf_symbols; 2132dc36bedSjoris TAILQ_HEAD(rcs_llist, rcs_lock) rf_locks; 2142dc36bedSjoris 2152dc36bedSjoris void *rf_pdata; 2162dc36bedSjoris } RCSFILE; 2172dc36bedSjoris 2182dc36bedSjoris extern int rcs_errno; 2192dc36bedSjoris 220bc8d37c3Sjoris RCSFILE *rcs_open(const char *, int, int, ...); 2212dc36bedSjoris void rcs_close(RCSFILE *); 2222dc36bedSjoris int rcs_head_set(RCSFILE *, RCSNUM *); 2232dc36bedSjoris const RCSNUM *rcs_branch_get(RCSFILE *); 2242dc36bedSjoris int rcs_access_add(RCSFILE *, const char *); 2252dc36bedSjoris int rcs_access_remove(RCSFILE *, const char *); 2262dc36bedSjoris struct rcs_delta *rcs_findrev(RCSFILE *, RCSNUM *); 2272dc36bedSjoris int rcs_sym_add(RCSFILE *, const char *, RCSNUM *); 2282dc36bedSjoris int rcs_sym_remove(RCSFILE *, const char *); 2292dc36bedSjoris RCSNUM *rcs_sym_getrev(RCSFILE *, const char *); 2302dc36bedSjoris int rcs_sym_check(const char *); 2312dc36bedSjoris int rcs_lock_getmode(RCSFILE *); 2322dc36bedSjoris int rcs_lock_setmode(RCSFILE *, int); 2332dc36bedSjoris int rcs_lock_add(RCSFILE *, const char *, RCSNUM *); 2342dc36bedSjoris int rcs_lock_remove(RCSFILE *, const char *, RCSNUM *); 2352dc36bedSjoris BUF *rcs_getrev(RCSFILE *, RCSNUM *); 2363de4517bSniallo int rcs_deltatext_set(RCSFILE *, RCSNUM *, BUF *); 2372dc36bedSjoris void rcs_desc_set(RCSFILE *, const char *); 2382dc36bedSjoris void rcs_comment_set(RCSFILE *, const char *); 2392dc36bedSjoris BUF *rcs_kwexp_buf(BUF *, RCSFILE *, RCSNUM *); 2402dc36bedSjoris void rcs_kwexp_set(RCSFILE *, int); 2412dc36bedSjoris int rcs_kwexp_get(RCSFILE *); 2422dc36bedSjoris int rcs_rev_add(RCSFILE *, RCSNUM *, const char *, time_t, 2432dc36bedSjoris const char *); 2442dc36bedSjoris time_t rcs_rev_getdate(RCSFILE *, RCSNUM *); 2452dc36bedSjoris int rcs_rev_setlog(RCSFILE *, RCSNUM *, const char *); 2462dc36bedSjoris int rcs_rev_remove(RCSFILE *, RCSNUM *); 2472dc36bedSjoris int rcs_state_set(RCSFILE *, RCSNUM *, const char *); 2482dc36bedSjoris int rcs_state_check(const char *); 24993acdb67Sxsa void rcs_write(RCSFILE *); 250be0b58deSxsa void rcs_delta_stats(struct rcs_delta *, int *, int *); 2512dc36bedSjoris 2522dc36bedSjoris int rcs_kflag_get(const char *); 2532dc36bedSjoris 2542dc36bedSjoris RCSNUM *rcsnum_alloc(void); 2552dc36bedSjoris RCSNUM *rcsnum_parse(const char *); 2562dc36bedSjoris RCSNUM *rcsnum_brtorev(const RCSNUM *); 2572dc36bedSjoris RCSNUM *rcsnum_revtobr(const RCSNUM *); 2582dc36bedSjoris RCSNUM *rcsnum_inc(RCSNUM *); 2592dc36bedSjoris void rcsnum_free(RCSNUM *); 260f66d1793Stobias int rcsnum_addmagic(RCSNUM *); 2611294ab80Sotto int rcsnum_aton(const char *, const char **, RCSNUM *); 2622dc36bedSjoris char *rcsnum_tostr(const RCSNUM *, char *, size_t); 2632dc36bedSjoris void rcsnum_cpy(const RCSNUM *, RCSNUM *, u_int); 2642dc36bedSjoris int rcsnum_cmp(const RCSNUM *, const RCSNUM *, u_int); 2652dc36bedSjoris 2662dc36bedSjoris /* rcstime.c */ 2672dc36bedSjoris void rcs_set_tz(char *, struct rcs_delta *, struct tm *); 2682dc36bedSjoris extern char *timezone_flag; 2692dc36bedSjoris extern int rcsnum_flags; 2702dc36bedSjoris 2712dc36bedSjoris #endif /* RCS_H */ 272