/*
 * Copyright (c) 2000-2009 TeamDev Ltd. All rights reserved.
 * TeamDev PROPRIETARY and CONFIDENTIAL.
 * Use is subject to license terms.
 */
package com.jniwrapper.win32.security;

import com.jniwrapper.*;

/**
 * This structure contains information about privileges for access token and corresponds to
 * native <code>TOKEN_GROUPS</code> structure.
 *
 * @author Vadim Ridosh
 */
public class TokenGroups extends Structure
{
    private UInt32 _groupCount = new UInt32() {
        public void acceptIOPerformer(IOPerformer performer,
                                         DataBuffer source,
                                         int initialOffset,
                                         boolean isReadOperation,
                                         boolean invokedByCallback)
        {
            super.acceptIOPerformer(performer, source, initialOffset, isReadOperation, invokedByCallback);
            _groups.setElementCount((int) getValue());
        }

        public void read(DataBuffer stackBuffer, int offset, boolean invokedByCallback)
                throws MemoryAccessViolationException
        {
            super.read(stackBuffer, offset, invokedByCallback);
            _groups.setElementCount((int) getValue());
        }
    };

    private ComplexArray _groups = new ComplexArray(new SidAndAttributes(), 0);
    private PrimitiveArray _padding = new PrimitiveArray(new UInt8(), 0); 

    public TokenGroups()
    {
        init(new Parameter[]{_groupCount, _groups, _padding}, (short)8);
    }

    public int getGroupCount()
    {
        return (int) _groupCount.getValue();
    }

    public void setGroupCount(int groupCount)
    {
        _groupCount.setValue(groupCount);
    }

    public SidAndAttributes getGroups(int index)
    {
        return (SidAndAttributes) _groups.getElement(index);
    }

    public Object clone()
    {
        TokenGroups tokenGroups = new TokenGroups();
        tokenGroups.initFrom(this);
        return tokenGroups;
    }

    /**
     * Should be called to set expected structure size.
     *
     * @param additionalSize size in bytes
     */
    public void setExpectedStructureSize(int additionalSize)
    {
        _padding = new PrimitiveArray(new UInt8(), additionalSize);
        init(new Parameter[]{_groupCount, _groups, _padding}, (short)8);
    }
}