/* -*- Mode: IDL; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
/*
 * The contents of this file are subject to the Mozilla Public License
 * Version 1.1 (the "MPL"); you may not use this file except in
 * compliance with the MPL.  You may obtain a copy of the MPL at
 * http://www.mozilla.org/MPL/
 *
 * Software distributed under the MPL is distributed on an "AS IS" basis,
 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the MPL
 * for the specific language governing rights and limitations under the
 * MPL.
 *
 * The Initial Developer of this code under the MPL is Netscape
 * Communications Corporation.  Portions created by Netscape are
 * Copyright (C) 1999 Netscape Communications Corporation.  All Rights
 * Reserved.
 */
#include "nsISupports.idl"
#include "nsIEnumerator.idl"

interface nsIFile;

typedef PRUint32 nsRegistryKey;
typedef long     nsWellKnownRegistry;

[scriptable,uuid(5D41A440-8E37-11d2-8059-00600811A9C3)]
interface nsIRegistry : nsISupports
{
    const long None = 0;
    const long Users = 1;
    const long Common = 2;
    const long CurrentUser = 3;

    const long ApplicationComponentRegistry = 1;
    const long ApplicationRegistry = 2;

    // Dont use this one. This for internal use only.
    const long ApplicationCustomRegistry = -1;

    void open(in nsIFile regFile);
    void openWellKnownRegistry(in nsWellKnownRegistry regid);

    void flush();
    boolean isOpen();
    
    nsRegistryKey addKey(in nsRegistryKey baseKey, in wstring keyname);
    nsRegistryKey getKey(in nsRegistryKey baseKey, in wstring keyname);
    void removeKey(in nsRegistryKey baseKey, in wstring keyname);

    wstring getString(in nsRegistryKey baseKey, in wstring valname);
    void setString(in nsRegistryKey baseKey, in wstring valname, in wstring value);

    string getStringUTF8(in nsRegistryKey baseKey, in string path);
    void setStringUTF8(in nsRegistryKey baseKey, in string path, in string value);

    void getBytesUTF8(in nsRegistryKey baseKey, in string path, out PRUint32 length, [retval, array, size_is(length)] out PRUint8 valueArray);
    void setBytesUTF8(in nsRegistryKey baseKey, in string path, in PRUint32 length, [array, size_is(length)] in PRUint8 valueArray);
    PRInt32 getInt(in nsRegistryKey baseKey, in string path);
    void setInt(in nsRegistryKey baseKey, in string path, in PRInt32 value);
    PRInt64 getLongLong(in nsRegistryKey baseKey, in string path);
    void setLongLong(in nsRegistryKey baseKey, in string path, inout PRInt64 value);

    /**
     * addSubtree() and friends need to be renamed to addKeyUTF8().
     * If you are using these forms make sure you pass UTF8 data
     */
    nsRegistryKey addSubtree(in nsRegistryKey baseKey, in string path);
    void removeSubtree(in nsRegistryKey baseKey, in string path);
    nsRegistryKey getSubtree(in nsRegistryKey baseKey, in string path);

    nsRegistryKey addSubtreeRaw(in nsRegistryKey baseKey, in string path);
    void removeSubtreeRaw(in nsRegistryKey baseKey, in string path);
    nsRegistryKey getSubtreeRaw(in nsRegistryKey baseKey, in string path);

    nsIEnumerator enumerateSubtrees(in nsRegistryKey baseKey);
    nsIEnumerator enumerateAllSubtrees(in nsRegistryKey baseKey);
    nsIEnumerator enumerateValues(in nsRegistryKey baseKey);
    
    const unsigned long String = 1;
    const unsigned long Int32 = 2;
    const unsigned long Bytes = 3;
    const unsigned long File = 4;
    
    unsigned long getValueType(in nsRegistryKey baseKey, in string path);
    PRUint32 getValueLength(in nsRegistryKey baseKey, in string path);
    void deleteValue(in nsRegistryKey baseKey, in string path);

    /**
     * escapeKey() takes arbitrary binary data and converts it into
     * valid ASCII which can be used as registry key or value names
     */
    void escapeKey([array, size_is(length)] in PRUint8 key, in PRUint32 terminator, inout PRUint32 length, [retval, array, size_is(length)] out PRUint8 escaped); 
    void unescapeKey([array, size_is(length)] in PRUint8 escaped, in PRUint32 terminator, inout PRUint32 length, [retval, array, size_is(length)] out PRUint8 key); 

    attribute string currentUserName;

    void pack();
};

[scriptable, uuid(8cecf236-1dd2-11b2-893c-f9848956eaec)]
interface nsIRegistryEnumerator : nsIEnumerator
{
    void currentItemInPlaceUTF8(out nsRegistryKey key,
                                [shared, retval] out string item);
};

[scriptable, uuid(D1B54831-AC07-11d2-805E-00600811A9C3)]
interface nsIRegistryNode : nsISupports
{
    readonly attribute string nameUTF8;
    readonly attribute wstring name;
    readonly attribute nsRegistryKey key;
};

[scriptable,uuid(5316C380-B2F8-11d2-A374-0080C6F80E4B)]
interface nsIRegistryValue : nsISupports
{
    readonly attribute wstring name;
    readonly attribute string nameUTF8;
    readonly attribute unsigned long type;
    readonly attribute PRUint32 length;
};

[uuid(3A15FC88-7A61-4Ab4-8E58-31E95fAB3DA8)]
/**
 * It sucks that nsIRegistry has to always allocate and return
 * strings. nsIRegistryGetter adds in interfaces for non allocating getters
 * to registry values.
 */
interface nsIRegistryGetter : nsISupports
{
    /**
     * Get a string value of attribute valname in widestring or utf8 format
     *
     * @return
     *  NS_OK on success.
     *    buf has the string value copied into it. length is NOT changed.
     *  NS_ERROR_REG_BUFFER_TOO_SMALL if not enough buffer space.
     *    length is updated to actual length in chars including
     *    terminating NULL and buf will be unchanged.
     *  NS_ERROR_FAILURE if an unknown error happened. state of buf and
     *    length undefined.
     *  various failure codes otherwise. buf and length wont be updated.
     */
    void getStringUTF8IntoBuffer(in nsRegistryKey baseKey, in string path,
                                 inout char buf, inout PRUint32 length);

    /**
     * Get a a byte array value of attribute valname
     *
     * @return
     *  NS_OK on success. buf has the string value copied into it.
     *    length is updated to actual number of bytes copied into buf.
     *  NS_ERROR_REG_BUFFER_TOO_SMALL if not enough buffer space.
     *    length is updated to actual length in PRUint8s including
     *    terminating NULL and buf will be unchanged.
     *  NS_ERROR_FAILURE if an unknown error happened. state of buf and
     *    length undefined.
     *  various other failure codes otherwise. buf and length wont be updated.
     */
    void getBytesUTF8IntoBuffer(in nsRegistryKey baseKey, in string path,
                                inout PRUint8 buf, inout PRUint32 length);
};

%{ C++
#include "nsIRegistryUtils.h"
%}
