2 Unix SMB/Netbios implementation.
5 Copyright (C) Andrew Tridgell 2001
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
26 /****************************************************************************
27 copy a string from a char* src to a unicode or ascii
28 dos code page destination choosing unicode or ascii based on the
29 cli->capabilities flag
30 return the number of bytes occupied by the string in the destination
32 STR_TERMINATE means include the null termination
33 STR_CONVERT means convert from unix to dos codepage
34 STR_UPPER means uppercase in the destination
35 STR_ASCII use ascii even with unicode servers
36 dest_len is the maximum length allowed in the destination. If dest_len
37 is -1 then no maxiumum is used
38 ****************************************************************************/
39 int clistr_push(struct cli_state *cli, void *dest, const char *src, int dest_len, int flags)
43 /* treat a pstring as "unlimited" length */
45 dest_len = sizeof(pstring);
48 if (!(flags & STR_ASCII) && clistr_align(cli->outbuf, dest)) {
50 dest = (void *)((char *)dest + 1);
55 if ((flags & STR_ASCII) || !(SVAL(cli->outbuf, smb_flg2) & FLAGS2_UNICODE_STRINGS)) {
56 /* the server doesn't want unicode */
57 safe_strcpy(dest, src, dest_len);
59 if (flags & STR_TERMINATE) len++;
60 if (flags & STR_CONVERT) unix_to_dos(dest,True);
61 if (flags & STR_UPPER) strupper(dest);
65 /* the server likes unicode. give it the works */
66 if (flags & STR_CONVERT) {
67 dos_PutUniCode(dest, src, dest_len, flags & STR_TERMINATE);
69 ascii_to_unistr(dest, src, dest_len);
71 if (flags & STR_UPPER) {
75 if (flags & STR_TERMINATE) len += 2;
79 /****************************************************************************
80 copy a string from a unicode or ascii source (depending on
81 cli->capabilities) to a char* destination
83 STR_CONVERT means convert from dos to unix codepage
84 STR_TERMINATE means the string in src is null terminated
85 STR_UNICODE means to force as unicode
86 if STR_TERMINATE is set then src_len is ignored
87 src_len is the length of the source area in bytes
88 return the number of bytes occupied by the string in src
89 ****************************************************************************/
90 int clistr_pull(struct cli_state *cli, char *dest, const void *src, int dest_len, int src_len, int flags)
95 dest_len = sizeof(pstring);
98 if (!(flags & STR_ASCII) && clistr_align(cli->inbuf, src)) {
99 src = (void *)((char *)src + 1);
100 if (src_len > 0) src_len--;
103 if ((flags & STR_ASCII) ||
104 (!(flags & STR_UNICODE) && !(SVAL(cli->inbuf, smb_flg2) & FLAGS2_UNICODE_STRINGS))) {
105 /* the server doesn't want unicode */
106 if (flags & STR_TERMINATE) {
107 safe_strcpy(dest, src, dest_len);
110 if (src_len > dest_len) src_len = dest_len;
112 memcpy(dest, src, len);
115 if (flags & STR_CONVERT) dos_to_unix(dest,True);
119 if (flags & STR_TERMINATE) {
120 unistr_to_ascii(dest, src, dest_len);
121 len = strlen(dest)*2 + 2;
124 if (dest_len*2 < src_len) src_len = 2*dest_len;
125 for (i=0; i < src_len; i += 2) {
132 if (flags & STR_CONVERT) dos_to_unix(dest,True);
137 /****************************************************************************
138 return an alignment of either 0 or 1
139 if unicode is not negotiated then return 0
140 otherwise return 1 if offset is off
141 ****************************************************************************/
142 int clistr_align(const void *buf, const void *p)
144 if (!(SVAL(buf, smb_flg2) & FLAGS2_UNICODE_STRINGS)) return 0;
145 return PTR_DIFF(p, buf) & 1;