1 /* $NetBSD: v_put.c,v 1.3 2014/01/26 21:43:45 christos Exp $ */ 2 /*- 3 * Copyright (c) 1992, 1993, 1994 4 * The Regents of the University of California. All rights reserved. 5 * Copyright (c) 1992, 1993, 1994, 1995, 1996 6 * Keith Bostic. All rights reserved. 7 * 8 * See the LICENSE file for redistribution information. 9 */ 10 11 #include "config.h" 12 13 #include <sys/cdefs.h> 14 #if 0 15 #ifndef lint 16 static const char sccsid[] = "Id: v_put.c,v 10.6 2001/06/25 15:19:34 skimo Exp (Berkeley) Date: 2001/06/25 15:19:34 "; 17 #endif /* not lint */ 18 #else 19 __RCSID("$NetBSD: v_put.c,v 1.3 2014/01/26 21:43:45 christos Exp $"); 20 #endif 21 22 #include <sys/types.h> 23 #include <sys/queue.h> 24 #include <sys/time.h> 25 26 #include <bitstring.h> 27 #include <limits.h> 28 #include <stdio.h> 29 30 #include "../common/common.h" 31 #include "vi.h" 32 33 static void inc_buf __P((SCR *, VICMD *)); 34 35 /* 36 * v_Put -- [buffer]P 37 * Insert the contents of the buffer before the cursor. 38 * 39 * PUBLIC: int v_Put __P((SCR *, VICMD *)); 40 */ 41 int 42 v_Put(SCR *sp, VICMD *vp) 43 { 44 u_long cnt; 45 46 if (F_ISSET(vp, VC_ISDOT)) 47 inc_buf(sp, vp); 48 49 /* 50 * !!! 51 * Historic vi did not support a count with the 'p' and 'P' 52 * commands. It's useful, so we do. 53 */ 54 for (cnt = F_ISSET(vp, VC_C1SET) ? vp->count : 1; cnt--;) { 55 if (put(sp, NULL, 56 F_ISSET(vp, VC_BUFFER) ? &vp->buffer : NULL, 57 &vp->m_start, &vp->m_final, 0)) 58 return (1); 59 vp->m_start = vp->m_final; 60 if (INTERRUPTED(sp)) 61 return (1); 62 } 63 return (0); 64 } 65 66 /* 67 * v_put -- [buffer]p 68 * Insert the contents of the buffer after the cursor. 69 * 70 * PUBLIC: int v_put __P((SCR *, VICMD *)); 71 */ 72 int 73 v_put(SCR *sp, VICMD *vp) 74 { 75 u_long cnt; 76 77 if (F_ISSET(vp, VC_ISDOT)) 78 inc_buf(sp, vp); 79 80 /* 81 * !!! 82 * Historic vi did not support a count with the 'p' and 'P' 83 * commands. It's useful, so we do. 84 */ 85 for (cnt = F_ISSET(vp, VC_C1SET) ? vp->count : 1; cnt--;) { 86 if (put(sp, NULL, 87 F_ISSET(vp, VC_BUFFER) ? &vp->buffer : NULL, 88 &vp->m_start, &vp->m_final, 1)) 89 return (1); 90 vp->m_start = vp->m_final; 91 if (INTERRUPTED(sp)) 92 return (1); 93 } 94 return (0); 95 } 96 97 /* 98 * !!! 99 * Historical whackadoo. The dot command `puts' the numbered buffer 100 * after the last one put. For example, `"4p.' would put buffer #4 101 * and buffer #5. If the user continued to enter '.', the #9 buffer 102 * would be repeatedly output. This was not documented, and is a bit 103 * tricky to reconstruct. Historical versions of vi also dropped the 104 * contents of the default buffer after each put, so after `"4p' the 105 * default buffer would be empty. This makes no sense to me, so we 106 * don't bother. Don't assume sequential order of numeric characters. 107 * 108 * And, if that weren't exciting enough, failed commands don't normally 109 * set the dot command. Well, boys and girls, an exception is that 110 * the buffer increment gets done regardless of the success of the put. 111 */ 112 static void 113 inc_buf(SCR *sp, VICMD *vp) 114 { 115 CHAR_T v; 116 117 switch (vp->buffer) { 118 case '1': 119 v = '2'; 120 break; 121 case '2': 122 v = '3'; 123 break; 124 case '3': 125 v = '4'; 126 break; 127 case '4': 128 v = '5'; 129 break; 130 case '5': 131 v = '6'; 132 break; 133 case '6': 134 v = '7'; 135 break; 136 case '7': 137 v = '8'; 138 break; 139 case '8': 140 v = '9'; 141 break; 142 default: 143 return; 144 } 145 VIP(sp)->sdot.buffer = vp->buffer = v; 146 } 147