Merge from vendor branch GDB:
[dragonfly.git] / gnu / usr.bin / as / bignum-copy.c
1 /* bignum_copy.c - copy a bignum
2    Copyright (C) 1987, 1990, 1991, 1992 Free Software Foundation, Inc.
3
4    This file is part of GAS, the GNU Assembler.
5
6    GAS is free software; you can redistribute it and/or modify
7    it under the terms of the GNU General Public License as published by
8    the Free Software Foundation; either version 2, or (at your option)
9    any later version.
10
11    GAS is distributed in the hope that it will be useful,
12    but WITHOUT ANY WARRANTY; without even the implied warranty of
13    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14    GNU General Public License for more details.
15
16    You should have received a copy of the GNU General Public License
17    along with GAS; see the file COPYING.  If not, write to
18    the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
19
20 /*
21  * $FreeBSD: src/gnu/usr.bin/as/bignum-copy.c,v 1.6 1999/08/27 23:34:12 peter Exp $
22  * $DragonFly: src/gnu/usr.bin/as/Attic/bignum-copy.c,v 1.2 2003/06/17 04:25:44 dillon Exp $
23  */
24 #include "as.h"
25
26 /*
27  *                      bignum_copy ()
28  *
29  * Copy a bignum from in to out.
30  * If the output is shorter than the input, copy lower-order littlenums.
31  * Return 0 or the number of significant littlenums dropped.
32  * Assumes littlenum arrays are densely packed: no unused chars between
33  * the littlenums. Uses memcpy() to move littlenums, and wants to
34  * know length (in chars) of the input bignum.
35  */
36
37 /* void */
38 int
39     bignum_copy(in, in_length, out, out_length)
40 register LITTLENUM_TYPE *in;
41 register int in_length; /* in sizeof(littlenum)s */
42 register LITTLENUM_TYPE *out;
43 register int out_length; /* in sizeof(littlenum)s */
44 {
45         int significant_littlenums_dropped;
46
47         if (out_length < in_length) {
48                 LITTLENUM_TYPE *p; /* -> most significant (non-zero) input
49                                       littlenum. */
50
51                 memcpy((void *) out, (void *) in,
52                       out_length << LITTLENUM_SHIFT);
53                 for (p = in + in_length - 1; p >= in; --p) {
54                         if (* p) break;
55                 }
56                 significant_littlenums_dropped = p - in - in_length + 1;
57
58                 if (significant_littlenums_dropped < 0) {
59                         significant_littlenums_dropped = 0;
60                 }
61         } else {
62                 memcpy((char *) out, (char *) in,
63                       in_length << LITTLENUM_SHIFT);
64
65                 if (out_length > in_length) {
66                         memset((char *) (out + out_length),
67                               '\0', (out_length - in_length) << LITTLENUM_SHIFT);
68                 }
69
70                 significant_littlenums_dropped = 0;
71         }
72
73         return(significant_littlenums_dropped);
74 } /* bignum_copy() */
75
76 /* end of bignum-copy.c */