1/*
2 * Unix SMB/CIFS implementation.
3 * Copyright (C) Jeremy Allison 1995-1998
4 * Copyright (C) Tim Potter     2001
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License as published by the
8 * Free Software Foundation; either version 2 of the License, or (at your
9 * option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
14 * more details.
15 *
16 * You should have received a copy of the GNU General Public License along with
17 * this program; if not, write to the Free Software Foundation, Inc., 675
18 * Mass Ave, Cambridge, MA 02139, USA.  */
19
20#include "includes.h"
21
22#if 1
23  #define P1MSG(args...)
24#else
25  #define P1MSG(args...) fprintf(stderr, "%s-%04d: ", __FILE__, __LINE__) ; fprintf(stderr, ## args)
26#endif // NDEBUG
27#if 0
28//ori: /lib/util_unistr.c
29/*******************************************************************
30 Count the number of characters in a smb_ucs2_t string.
31********************************************************************/
32size_t strlen_w(const smb_ucs2_t *src)
33{
34    size_t len;
35
36    for(len = 0; *src++; len++) ;
37
38    return len;
39}
40
41//ori: smbencrypt.c
42/**
43 * Creates the DES forward-only Hash of the users password in DOS ASCII charset
44 * @param passwd password in 'unix' charset.
45 * @param p16 return password hashed with DES, caller allocated 16 byte buffer
46 * @return False if password was > 14 characters, and therefore may be incorrect, otherwise True
47 * @note p16 is filled in regardless
48 */
49
50BOOL E_deshash(const char *passwd, uchar p16[16])
51{
52    BOOL ret = True;
53    fstring dospwd;
54    ZERO_STRUCT(dospwd);
55
56    /* Password must be converted to DOS charset - null terminated, uppercase. */
57    //push_ascii(dospwd, passwd, sizeof(dospwd), STR_UPPER|STR_TERMINATE);
58    {
59        int i;
60
61        if (passwd == 0)
62            return 0;
63        i = 0;
64        while(1)
65        {
66            if(passwd[i] == 0)
67            {
68                dospwd[i] = 0;
69                break;
70            }
71            else
72            {
73                dospwd[i] = toupper(passwd);
74            }
75            i++;
76        }
77    }
78
79    /* Only the fisrt 14 chars are considered, password need not be null terminated. */
80    E_P16((const unsigned char *)dospwd, p16);
81
82    if (strlen(dospwd) > 14) {
83        ret = False;
84    }
85
86    ZERO_STRUCT(dospwd);
87
88    return ret;
89}
90
91//ori: smbencrypt.c
92/**
93 * Creates the MD4 Hash of the users password in NT UNICODE.
94 * @param passwd password in 'unix' charset.
95 * @param p16 return password hashed with md4, caller allocated 16 byte buffer
96 */
97
98void E_md4hash(const char *passwd, uchar p16[16])
99{
100    int len;
101    smb_ucs2_t wpwd[129];
102
103    /* Password must be converted to NT unicode - null terminated. */
104    //push_ucs2(NULL, wpwd, (const char *)passwd, 256, STR_UNICODE|STR_NOALIGN|STR_TERMINATE);
105    /* Calculate length in bytes */
106    len = strlen_w(wpwd) * sizeof(int16);
107
108    mdfour(p16, (unsigned char *)wpwd, len);
109    ZERO_STRUCT(wpwd);
110}
111
112#endif //if 0
113#define SAMBA_NO_PASSWD "NO PASSWORDXXXXXXXXXXXXXXXXXXXXX"
114#define SAMBA_CTL_PWNOTREQ "[NU         ]"
115#define SAMBA_CTL_NORMAL "[U          ]"
116
117/*********************************************************
118 Start here.
119**********************************************************/
120int main(int argc, char **argv)
121{
122
123    int i;
124    uchar new_lanman_p16[LM_HASH_LEN];
125    uchar new_nt_p16[NT_HASH_LEN];
126    char lanPW[LM_HASH_LEN * 2 + 1];
127    char ntPW[NT_HASH_LEN * 2 + 1];
128    char *tmp;
129    FILE *fp;
130
131    if (argc == 2 || argc == 3 )
132    {
133        fp  = fopen("/usr/local/samba/private/smbpasswd", "a");
134
135        if (argc == 3)
136        {
137        //==================
138        //create hashs
139        //==================
140            memset(lanPW, 0, LM_HASH_LEN * 2 + 1);
141            memset(ntPW, 0, NT_HASH_LEN * 2 + 1);
142            E_md4hash(argv[2], new_nt_p16);
143
144            for(i=0; i<NT_HASH_LEN; i++)
145            {
146                asprintf(&tmp, "%.2X", new_nt_p16[i]);
147                ntPW[i*2] = tmp[0];
148                ntPW[i*2 + 1] = tmp[1];
149                free(tmp);
150            }
151
152            if (!E_deshash(argv[2], new_lanman_p16)) {
153                fprintf(stderr, "E_deshash failed\n");
154                return -1;
155            }
156
157            for(i=0; i<LM_HASH_LEN; i++)
158            {
159                asprintf(&tmp, "%.2X", new_lanman_p16[i]);
160                lanPW[i*2] = tmp[0];
161                lanPW[i*2 + 1] = tmp[1];
162                free(tmp);
163            }
164        //==================
165        //save to smbpasswd
166        //==================
167            P1MSG("save \"%s:0:%s:%s:%s:LCT-3E12A0AC:\"\n", argv[1], lanPW, ntPW, SAMBA_CTL_NORMAL);
168            if (fp)
169            {
170                fprintf(fp, "%s:0:%s:%s:%s:LCT-3E12A0AC:\n", argv[1], lanPW, ntPW, SAMBA_CTL_NORMAL);
171            }
172            else
173            {
174                perror("open smb file faild: ");
175            }
176        } //if (argc == 3)
177        else
178        {
179        //======================
180        //arg == 2, no password
181        //======================
182            P1MSG("save \"%s:0:%s:%s:%s:LCT-3E12A0AC:\"\n", argv[1], SAMBA_NO_PASSWD, SAMBA_NO_PASSWD, SAMBA_CTL_PWNOTREQ);
183            if (fp)
184            {
185                fprintf(fp, "%s:0:%s:%s:%s:LCT-3E12A0AC:\n", argv[1], SAMBA_NO_PASSWD, SAMBA_NO_PASSWD, SAMBA_CTL_PWNOTREQ);
186            }
187            else
188            {
189                perror("open smb file faild: ");
190            }
191        } // agc == 2.
192
193        if (fp)
194        {
195           fclose(fp);
196        }
197    }
198    else
199    {
200        printf("usage smb_pass user passwd\n");
201    }
202    return 0;
203}
204