[squid-users] Kerberos pac ResourceGroups parsing

Alex Rousskov rousskov at measurement-factory.com
Wed Nov 22 16:22:13 UTC 2023


On 2023-11-21 23:05, Andrey K wrote:

> I have posted a PR: https://github.com/squid-cache/squid/pull/1597 
> 
> This is my first contribution to open source. Could you please verify if 
> everything is OK.

Thank you for posting that pull request! Let's continue this 
conversation on GitHub since squid-users mailing list is not meant for 
code reviews.

Alex.


> чт, 16 нояб. 2023 г. в 17:01, Alex Rousskov:
> 
>     On 2023-11-16 07:48, Andrey K wrote:
> 
>      > I have slightly patched the negotiate_kerberos_pac.cc to
>      > implement ResourceGropIds-block parsing.
> 
>     Please consider posting tested changes as a GitHub Pull Request:
>     https://wiki.squid-cache.org/MergeProcedure#pull-request
>     <https://wiki.squid-cache.org/MergeProcedure#pull-request>
> 
> 
>     Thank you,
> 
>     Alex.
> 
> 
>      > Maybe it will be useful for the community.
>      > This patch can be included in future Squid-releases.
>      >
>      > Kind regards,
>      >     Ankor.
>      >
>      > The patch for the
>      > file src/auth/negotiate/kerberos/negotiate_kerberos_pac.cc below:
>      >
>      > @@ -362,6 +362,123 @@
>      >       return ad_groups;
>      >   }
>      >
>      > +
>      > +char *
>      > +get_resource_group_domain_sid(uint32_t ResourceGroupDomainSid){
>      > +
>      > +    if (ResourceGroupDomainSid!= 0) {
>      > +        uint8_t rev;
>      > +        uint64_t idauth;
>      > +        char dli[256];
>      > +        char *ag;
>      > +        int l;
>      > +
>      > +        align(4);
>      > +
>      > +        uint32_t nauth = get4byt();
>      > +
>      > +        size_t length = 1+1+6+nauth*4;
>      > +
>      > +            ag=(char *)xcalloc((length+1)*sizeof(char),1);
>      > +            // the first byte is a length of the SID
>      > +            ag[0] = (char) length;
>      > +            memcpy((void *)&ag[1],(const void*)&p[bpos],1);
>      > +            memcpy((void *)&ag[2],(const void*)&p[bpos+1],1);
>      > +            ag[2] = ag[2]+1;
>      > +            memcpy((void *)&ag[3],(const
>     void*)&p[bpos+2],6+nauth*4);
>      > +
>      > +
>      > +
>      > +        /* mainly for debug only */
>      > +        rev = get1byt();
>      > +        bpos = bpos + 1; /*nsub*/
>      > +        idauth = get6byt_be();
>      > +
>      > +        snprintf(dli,sizeof(dli),"S-%d-%lu",rev,(long unsigned
>     int)idauth);
>      > +        for ( l=0; l<(int)nauth; l++ ) {
>      > +            uint32_t sauth;
>      > +            sauth = get4byt();
>      > +            snprintf((char
>      > *)&dli[strlen(dli)],sizeof(dli)-strlen(dli),"-%u",sauth);
>      > +        }
>      > +        debug((char *) "%s| %s: INFO: Got ResourceGroupDomainSid
>     %s\n",
>      > LogTime(), PROGRAM, dli);
>      > +        return ag;
>      > +    }
>      > +
>      > +    return NULL;
>      > +}
>      > +
>      > +char *
>      > +get_resource_groups(char *ad_groups, char
>     *resource_group_domain_sid,
>      > uint32_t ResourceGroupIds, uint32_t ResourceGroupCount){
>      > +    size_t group_domain_sid_len = resource_group_domain_sid[0];
>      > +    char *ag;
>      > +    size_t length;
>      > +
>      > +    resource_group_domain_sid++; //now it points to the actual data
>      > +
>      > +
>      > +    if (ResourceGroupIds!= 0) {
>      > +        uint32_t ngroup;
>      > +        int l;
>      > +
>      > +        align(4);
>      > +        ngroup = get4byt();
>      > +        if ( ngroup != ResourceGroupCount) {
>      > +            debug((char *) "%s| %s: ERROR: Group encoding error =>
>      > ResourceGroupCount: %d Array size: %d\n",
>      > +                  LogTime(), PROGRAM, ResourceGroupCount, ngroup);
>      > +            return NULL;
>      > +        }
>      > +        debug((char *) "%s| %s: INFO: Found %d Resource Group
>     rids\n",
>      > LogTime(), PROGRAM, ResourceGroupCount);
>      > +
>      > +        //make a group template which begins with the
>     ResourceGroupDomainID
>      > +        length = group_domain_sid_len+4;  //+4 for a rid
>      > +        ag=(char *)xcalloc(length*sizeof(char),1);
>      > +        memcpy((void *)ag,(const void*)resource_group_domain_sid,
>      > group_domain_sid_len);
>      > +
>      > +
>      > +        for ( l=0; l<(int)ResourceGroupCount; l++) {
>      > +            uint32_t sauth;
>      > +            memcpy((void *)&ag[group_domain_sid_len],(const
>      > void*)&p[bpos],4);
>      > +
>      > +            if (!pstrcat(ad_groups," group=")) {
>      > +                debug((char *) "%s| %s: WARN: Too many groups !
>     size >
>      > %d : %s\n",
>      > +                      LogTime(), PROGRAM, MAX_PAC_GROUP_SIZE,
>     ad_groups);
>      > +               xfree(ag);
>      > +               return NULL;
>      > +            }
>      > +
>      > +
>      > +            struct base64_encode_ctx ctx;
>      > +            base64_encode_init(&ctx);
>      > +            const uint32_t expectedSz =
>     base64_encode_len(length) +1 /*
>      > terminator */;
>      > +            char *b64buf = static_cast<char
>     *>(xcalloc(expectedSz, 1));
>      > +            size_t blen = base64_encode_update(&ctx, b64buf,
>     length,
>      > reinterpret_cast<uint8_t*>(ag));
>      > +            blen += base64_encode_final(&ctx, b64buf+blen);
>      > +            b64buf[expectedSz-1] = '\0';
>      > +            if (!pstrcat(ad_groups,
>     reinterpret_cast<char*>(b64buf))) {
>      > +                debug((char *) "%s| %s: WARN: Too many groups !
>     size >
>      > %d : %s\n",
>      > +                      LogTime(), PROGRAM, MAX_PAC_GROUP_SIZE,
>     ad_groups);
>      > +               xfree(ag);
>      > +               xfree(b64buf);
>      > +               return NULL;
>      > +            }
>      > +            xfree(b64buf);
>      > +
>      > +
>      > +
>      > +            sauth = get4byt();
>      > +            debug((char *) "%s| %s: Info: Got rid: %u\n",
>     LogTime(),
>      > PROGRAM, sauth);
>      > +            /* attribute */
>      > +            bpos = bpos+4;
>      > +        }
>      > +
>      > +        xfree(ag);
>      > +       return ad_groups;
>      > +    }
>      > +
>      > +    return NULL;
>      > +}
>      > +
>      > +
>      >   char *
>      >   get_ad_groups(char *ad_groups, krb5_context context, krb5_pac pac)
>      >   {
>      > @@ -379,14 +496,14 @@
>      >       uint32_t LogonDomainId=0;
>      >       uint32_t SidCount=0;
>      >       uint32_t ExtraSids=0;
>      > -    /*
>      >       uint32_t ResourceGroupDomainSid=0;
>      >       uint32_t ResourceGroupCount=0;
>      >       uint32_t ResourceGroupIds=0;
>      > -    */
>      >       char **Rids=NULL;
>      >       int l=0;
>      >
>      > +    char * resource_group_domain_sid=NULL;
>      > +
>      >       if (!ad_groups) {
>      >           debug((char *) "%s| %s: ERR: No space to store groups\n",
>      >                 LogTime(), PROGRAM);
>      > @@ -454,11 +571,11 @@
>      >       bpos = bpos+40;
>      >       SidCount = get4byt();
>      >       ExtraSids = get4byt();
>      > -    /* 4 bytes ResourceGroupDomainSid
>      > -     * 4 bytes ResourceGroupCount
>      > -     * 4 bytes ResourceGroupIds
>      > -     */
>      > -    bpos = bpos+12;
>      > +
>      > +    ResourceGroupDomainSid = get4byt();
>      > +    ResourceGroupCount = get4byt();
>      > +    ResourceGroupIds = get4byt();
>      > +
>      >       /*
>      >        * Read all data from structure => Now check pointers
>      >        */
>      > @@ -483,7 +600,15 @@
>      >       if ((ad_groups =
>     getextrasids(ad_groups,ExtraSids,SidCount))==NULL)
>      >           goto k5clean;
>      >
>      > +    resource_group_domain_sid =
>      > get_resource_group_domain_sid(ResourceGroupDomainSid);
>      > +    if(resource_group_domain_sid && ResourceGroupCount &&
>      > ResourceGroupIds){
>      > +        get_resource_groups(ad_groups, resource_group_domain_sid,
>      > ResourceGroupIds, ResourceGroupCount);
>      > +    }
>      > +
>      >       debug((char *) "%s| %s: INFO: Read %d of %d bytes \n",
>     LogTime(),
>      > PROGRAM, bpos, (int)ad_data->length);
>      > +
>      > +    if(resource_group_domain_sid) xfree(resource_group_domain_sid);
>      > +
>      >       if (Rids) {
>      >           for ( l=0; l<(int)GroupCount; l++) {
>      >               xfree(Rids[l]);
>      > @@ -493,6 +618,8 @@
>      >       krb5_free_data(context, ad_data);
>      >       return ad_groups;
>      >   k5clean:
>      > +    if(resource_group_domain_sid) xfree(resource_group_domain_sid);
>      > +
>      >       if (Rids) {
>      >           for ( l=0; l<(int)GroupCount; l++) {
>      >               xfree(Rids[l]);
>      >
>      > _______________________________________________
>      > squid-users mailing list
>      > squid-users at lists.squid-cache.org
>     <mailto:squid-users at lists.squid-cache.org>
>      > https://lists.squid-cache.org/listinfo/squid-users
>     <https://lists.squid-cache.org/listinfo/squid-users>
> 
>     _______________________________________________
>     squid-users mailing list
>     squid-users at lists.squid-cache.org
>     <mailto:squid-users at lists.squid-cache.org>
>     https://lists.squid-cache.org/listinfo/squid-users
>     <https://lists.squid-cache.org/listinfo/squid-users>
> 



More information about the squid-users mailing list