r23784: use the GPLv3 boilerplate as recommended by the FSF and the license text
[abartlet/samba.git/.git] / source3 / libads / authdata.c
index 2e7866c0559f314b91993e3279f34773727f49c7..d61ffc23978286f45b05318612653e15fc1e97fe 100644 (file)
@@ -10,7 +10,7 @@
    
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
-   the Free Software Foundation; either version 2 of the License, or
+   the Free Software Foundation; either version 3 of the License, or
    (at your option) any later version.
    
    This program is distributed in the hope that it will be useful,
@@ -19,8 +19,7 @@
    GNU General Public License for more details.
    
    You should have received a copy of the GNU General Public License
-   along with this program; if not, write to the Free Software
-   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+   along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */
 
 #include "includes.h"
@@ -42,24 +41,24 @@ static BOOL pac_io_logon_name(const char *desc, PAC_LOGON_NAME *logon_name,
        if (!prs_uint16("len", ps, depth, &logon_name->len))
                return False;
 
+       /* The following string is always in little endian 16 bit values,
+          copy as 8 bits to avoid endian reversal on big-endian machines.
+          len is the length in bytes. */
+
        if (UNMARSHALLING(ps) && logon_name->len) {
-               logon_name->username = PRS_ALLOC_MEM(ps, uint16, logon_name->len);
+               logon_name->username = PRS_ALLOC_MEM(ps, uint8, logon_name->len);
                if (!logon_name->username) {
                        DEBUG(3, ("No memory available\n"));
                        return False;
                }
        }
 
-       if (!prs_uint16s(True, "name", ps, depth, logon_name->username, 
-                        (logon_name->len / sizeof(uint16))))
+       if (!prs_uint8s(True, "name", ps, depth, logon_name->username, logon_name->len))
                return False;
 
        return True;
-
 }
 
-
-
 #if 0 /* Unused (handled now in net_io_user_info3()) - Guenther */
 static BOOL pac_io_krb_sids(const char *desc, KRB_SID_AND_ATTRS *sid_and_attr,
                            prs_struct *ps, int depth)
@@ -120,10 +119,14 @@ static BOOL pac_io_krb_sid_and_attr_array(const char *desc,
                return False;
 
        if (UNMARSHALLING(ps)) {
-               array->krb_sid_and_attrs = PRS_ALLOC_MEM(ps, KRB_SID_AND_ATTRS, num);
-               if (!array->krb_sid_and_attrs) {
-                       DEBUG(3, ("No memory available\n"));
-                       return False;
+               if (num) {
+                       array->krb_sid_and_attrs = PRS_ALLOC_MEM(ps, KRB_SID_AND_ATTRS, num);
+                       if (!array->krb_sid_and_attrs) {
+                               DEBUG(3, ("No memory available\n"));
+                               return False;
+                       }
+               } else {
+                       array->krb_sid_and_attrs = NULL;
                }
        }
 
@@ -184,10 +187,14 @@ static BOOL pac_io_group_membership_array(const char *desc,
                return False;
 
        if (UNMARSHALLING(ps)) {
-               array->group_membership = PRS_ALLOC_MEM(ps, GROUP_MEMBERSHIP, num);
-               if (!array->group_membership) {
-                       DEBUG(3, ("No memory available\n"));
-                       return False;
+               if (num) {
+                       array->group_membership = PRS_ALLOC_MEM(ps, GROUP_MEMBERSHIP, num);
+                       if (!array->group_membership) {
+                               DEBUG(3, ("No memory available\n"));
+                               return False;
+                       }
+               } else {
+                       array->group_membership = NULL;
                }
        }
 
@@ -443,10 +450,11 @@ static BOOL pac_io_pac_signature_data(const char *desc,
                                      PAC_SIGNATURE_DATA *data, uint32 length,
                                      prs_struct *ps, int depth)
 {
-       uint32 siglen = length - sizeof(uint32);
+       uint32 siglen = 0;
+
        prs_debug(ps, depth, desc, "pac_io_pac_signature_data");
        depth++;
-       
+
        if (data == NULL)
                return False;
 
@@ -455,11 +463,18 @@ static BOOL pac_io_pac_signature_data(const char *desc,
        if (!prs_uint32("type", ps, depth, &data->type))
                return False;
 
+       if ( length > sizeof(uint32) )
+               siglen = length - sizeof(uint32);       
+
        if (UNMARSHALLING(ps) && length) {
-               data->signature.buffer = PRS_ALLOC_MEM(ps, uint8, siglen);
-               if (!data->signature.buffer) {
-                       DEBUG(3, ("No memory available\n"));
-                       return False;
+               if (siglen) {
+                       data->signature.buffer = PRS_ALLOC_MEM(ps, uint8, siglen);
+                       if (!data->signature.buffer) {
+                               DEBUG(3, ("No memory available\n"));
+                               return False;
+                       }
+               } else {
+                       data->signature.buffer = NULL;
                }
        }
 
@@ -763,7 +778,7 @@ static void dump_pac_logon_info(PAC_LOGON_INFO *logon_info) {
        }
 }
 
-NTSTATUS decode_pac_data(TALLOC_CTX *mem_ctx,
+ NTSTATUS decode_pac_data(TALLOC_CTX *mem_ctx,
                         DATA_BLOB *pac_data_blob,
                         krb5_context context, 
                         krb5_keyblock *service_keyblock,
@@ -780,7 +795,7 @@ NTSTATUS decode_pac_data(TALLOC_CTX *mem_ctx,
        PAC_SIGNATURE_DATA *kdc_sig = NULL;
        PAC_LOGON_NAME *logon_name = NULL;
        PAC_LOGON_INFO *logon_info = NULL;
-       krb5_principal client_principal_pac;
+       krb5_principal client_principal_pac = NULL;
        NTTIME tgs_authtime_nttime;
        int i, srv_sig_pos = 0, kdc_sig_pos = 0;
        fstring username;
@@ -878,9 +893,9 @@ NTSTATUS decode_pac_data(TALLOC_CTX *mem_ctx,
        
                DEBUG(2,("decode_pac_data: Logon time mismatch between ticket and PAC!\n"));
                DEBUGADD(2, ("decode_pac_data: PAC: %s\n", 
-                       http_timestring(nt_time_to_unix(&logon_name->logon_time))));
+                       http_timestring(nt_time_to_unix(logon_name->logon_time))));
                DEBUGADD(2, ("decode_pac_data: Ticket: %s\n", 
-                       http_timestring(nt_time_to_unix(&tgs_authtime_nttime))));
+                       http_timestring(nt_time_to_unix(tgs_authtime_nttime))));
                
                nt_status = NT_STATUS_ACCESS_DENIED;
                goto out;
@@ -891,7 +906,7 @@ NTSTATUS decode_pac_data(TALLOC_CTX *mem_ctx,
                nt_status = NT_STATUS_INVALID_PARAMETER;
                goto out;
        }
-       rpcstr_pull(username, logon_name->username, sizeof(username), -1, STR_TERMINATE);
+       rpcstr_pull(username, logon_name->username, sizeof(username), logon_name->len, 0);
 
        ret = smb_krb5_parse_name_norealm(context, username, &client_principal_pac);
        if (ret) {
@@ -924,4 +939,20 @@ out:
        return nt_status;
 }
 
+ PAC_LOGON_INFO *get_logon_info_from_pac(PAC_DATA *pac_data) 
+{
+       PAC_LOGON_INFO *logon_info = NULL;
+       int i;
+       
+       for (i=0; i < pac_data->num_buffers; i++) {
+
+               if (pac_data->pac_buffer[i].type != PAC_TYPE_LOGON_INFO)
+                       continue;
+
+               logon_info = pac_data->pac_buffer[i].ctr->pac.logon_info;
+               break;
+       }
+       return logon_info;
+}
+
 #endif