/*
CLASS {NATIVE_Configuration|_CSharp}, NATIVE:

*/
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using Microsoft.Win32;
using AL4;

public class AL4_configuration
{
    
    public static List<AL4_configuration> All_configs = 
        new List<AL4_configuration>();

    public static int Create_new_configure(int Area, 
        string Path, string Name, bool Write, bool Create)
    {
        int i = All_configs.IndexOf(null);
        if (i < 0)
        {
            i = All_configs.Count;
            All_configs.Add(null);
        }
        All_configs[i] = new AL4_configuration(Area, Path, Name, Write, Create);
        return i;
    }

    
    string Key_name;
    bool Read_only;
    bool Can_create;
    
    public AL4_configuration(int Area, string Path, string Name, bool Write,
        bool Create)
    {
        Key_name = Path;
        if (Area == 1 && !starting(Key_name, "HKEY_")) 
            Key_name = "HKEY_LOCAL_MACHINE\\" + Key_name;
        else if (Area == 0 && !starting(Key_name, "HKEY_"))
            Key_name = "HKEY_CURRENT_USER\\Software\\" + Name +
            "\\" + Key_name;
        Read_only = !Write;
        Can_create = Create;
    }
    
    public static string Value_string(int Handle, 
        string Name_value, string New_value, bool Set_new)
    {
        AL4_configuration config = All_configs[Handle];
        String RESULT = "";
        try {
	        RESULT = (String) Registry.GetValue(
	            config.Key_name, Name_value, null);
        } catch { }
        if (RESULT == null)
        {
            RESULT = "";
            if (!config.Can_create) return RESULT;
        }
        if (Set_new && !config.Read_only)
            Registry.SetValue(config.Key_name, Name_value, New_value);
        return RESULT;
    }
    
    public static int Value_integer(int Handle, 
        string Name_value, int New_value, bool Set_new)
    {
        AL4_configuration config = All_configs[Handle];
        Object RESULT = Registry.GetValue(
            config.Key_name, Name_value, null);
        if (RESULT == null)
        {
            RESULT = (Object) 0;
            if (!config.Can_create) return 0;
        }
        if (Set_new && !config.Read_only)
            Registry.SetValue(config.Key_name, Name_value, New_value);
        return (int) RESULT;
    }
    
    public static bool Value_boolean(int Handle, 
        string Name_value, bool New_value, bool Set_new)
    {
        AL4_configuration config = All_configs[Handle];
        Object RESULT = Registry.GetValue(
            config.Key_name, Name_value, null);
        if (RESULT == null)
        {
            RESULT = (Object) false;
            if (!config.Can_create) return false;
        }
        if (Set_new && !config.Read_only)
            Registry.SetValue(config.Key_name, Name_value, New_value ? 1 : 0);
        
        try
        {
            return ((int) RESULT) != 0;
        }
        catch
        {
            return false;
        }
    }
    
    public static string Binary_get(int Handle, string Name_value)
    {
        string Result = "";
        AL4_configuration config = All_configs[Handle];
        try
        {
            Object obj = Registry.GetValue(
                config.Key_name, Name_value, null);
            Byte[] buf = (Byte[])obj;
            for (int i = 0; i < buf.Length; i++)
                Result += (char)buf[i];
        }
        catch (Exception E) 
        {
            AL4_system.Any_exception(E);
        }
        return Result;
    }

    
    
    public static bool Value_present(int Handle, string Name_value)
    {
        AL4_configuration config = All_configs[Handle];
        Object V = Registry.GetValue(
            config.Key_name, Name_value, null);
        return V != null;
    }
    
    public static void Value_delete(int Handle, string Name_value)
    {
        AL4_configuration config = All_configs[Handle];
        RegistryKey key = config.create_key(config.Key_name);
        if (Registry.GetValue(config.Key_name, Name_value, null) != null)
            key.DeleteValue(Name_value);
    }
    
    public static void Subkey_delete(int Handle, string Name_subkey)
    {
    	try {
	        AL4_configuration config = All_configs[Handle];
	        RegistryKey key = config.create_key(config.Key_name);
	        RegistryKey subkey = key.OpenSubKey(Name_subkey);
	        if (subkey != null) {
	        	subkey = null;
	        	key.DeleteSubKeyTree(Name_subkey);
	        }
    	}
    	catch { }
    }
    
    public static void Values_list(int Handle, ArrayStr List)
    {
        List.Clear();
        AL4_configuration config = All_configs[Handle];
        RegistryKey key = config.create_key(config.Key_name);
        foreach (string name in key.GetValueNames())
            List.Add(name);
    }
    
    public static void Subkeys_list(int Handle, ArrayStr List)
    {
        List.Clear();
        AL4_configuration config = All_configs[Handle];
        RegistryKey key = config.create_key(config.Key_name);
        foreach (string name in key.GetSubKeyNames())
            List.Add(name);
    }
    
    private bool starting(string X, string Y)
    {
        return X.Length >= Y.Length &&
            X.Substring(0, Y.Length) == Y;
    }
    
    private RegistryKey create_key(string key_name)
    {
        string path = key_name;
        RegistryKey base_key = null;
        if (starting(path, "HKEY_CURRENT_USER\\"))
            base_key = Registry.CurrentUser;
        else if (starting(path, "HKEY_LOCAL_MACHINE\\"))
            base_key = Registry.LocalMachine;
        else if (starting(path, "HKEY_CURRENT_CONFIG\\"))
            base_key = Registry.CurrentConfig;
        else if (starting(path, "HKEY_CLASSES_ROOT\\"))
            base_key = Registry.ClassesRoot;
        else if (starting(path, "HKEY_PERFORMANCE_DATA\\"))
            base_key = Registry.PerformanceData;
        else if (starting(path, "HKEY_USERS"))
            base_key = Registry.Users;
        else return null;
        for (int i = 0; i < path.Length; i++)
            if (path[i] == '\\')
            {
                path = path.Substring(i+1, path.Length - i - 1);
                break;
            }
        return base_key.CreateSubKey(path);
    }
    /*
    
CONST STR:
    NATIVE_configure_import = ""

    NATIVE_new_configure_object = @
    "   RESULT = AL4_configuration.Create_new_configure("
    "       X_Area, X_Path, X_Name,"
    "       !X_Read, X_Can_create);"
    
    NATIVE_release_configure_object = @
    "   if (AL4_configuration.All_configs.Count > X_Handle && X_Handle >= 0)"
    "       AL4_configuration.All_configs[(int)X_Handle] = null;"
    
    NATIVE_value_string = @
    "   RESULT = AL4_configuration.Value_string("
    "       (int)X_Handle, X_Name, X_New, X_Set);"
    
    NATIVE_value_integer = @
    "   RESULT = AL4_configuration.Value_integer("
    "       (int)X_Handle, X_Name, (int)X_New, X_Set);"
    
    NATIVE_value_boolean = @
    "   RESULT = AL4_configuration.Value_boolean("
    "       (int)X_Handle, X_Name, X_New, X_Set);"
    
    NATIVE_binary_get = @
    "   RESULT = AL4_configuration.Binary_get((int)X_Handle, X_Name);"
    
    NATIVE_present_value = @
    "   RESULT = AL4_configuration.Value_present("
    "       (int)X_Handle, X_Name);"
    
    NATIVE_list_values = @
    "   AL4_configuration.Values_list((int)X_Handle, X_List);"
    
    NATIVE_list_subkeys = @
    "   AL4_configuration.Subkeys_list((int)X_Handle, X_List);"
    
    NATIVE_delete_value = @
    "   AL4_configuration.Value_delete((int)X_Handle, X_Name);"
    
    NATIVE_delete_subkey = @
    "   AL4_configuration.Subkey_delete((int)X_Handle, X_Name);"

    .
        
END
*/

}
