Merge with trunk r37677
[blender.git] / source / blender / makesrna / intern / rna_access.c
index 4cc5ca6..a632c5c 100644 (file)
@@ -1,4 +1,4 @@
-/**
+/*
  * $Id$
  *
  * ***** BEGIN GPL LICENSE BLOCK *****
  * ***** END GPL LICENSE BLOCK *****
  */
 
+/** \file blender/makesrna/intern/rna_access.c
+ *  \ingroup RNA
+ */
+
+
 #include <stdlib.h>
+#include <stddef.h>
 #include <string.h>
 #include <ctype.h>
 
@@ -33,6 +39,7 @@
 #include "DNA_windowmanager_types.h"
 
 #include "BLI_blenlib.h"
+#include "BLI_utildefines.h"
 #include "BLI_dynstr.h"
 #include "BLI_ghash.h"
 
 #include "BKE_idprop.h"
 #include "BKE_main.h"
 #include "BKE_report.h"
-#include "BKE_utildefines.h"
+
 
 #include "WM_api.h"
 
 #include "RNA_access.h"
 #include "RNA_define.h"
-#include "RNA_types.h"
 
 /* flush updates */
 #include "DNA_object_types.h"
 
 #include "rna_internal.h"
 
+const PointerRNA PointerRNA_NULL= {{NULL}};
+
 /* Init/Exit */
 
-void RNA_init()
+void RNA_init(void)
 {
        StructRNA *srna;
        PropertyRNA *prop;
 
        for(srna=BLENDER_RNA.structs.first; srna; srna=srna->cont.next) {
                if(!srna->cont.prophash) {
-                       srna->cont.prophash= BLI_ghash_new(BLI_ghashutil_strhash, BLI_ghashutil_strcmp);
+                       srna->cont.prophash= BLI_ghash_new(BLI_ghashutil_strhash, BLI_ghashutil_strcmp, "RNA_init gh");
 
                        for(prop=srna->cont.properties.first; prop; prop=prop->next)
                                if(!(prop->flag & PROP_BUILTIN))
@@ -74,7 +82,7 @@ void RNA_init()
        }
 }
 
-void RNA_exit()
+void RNA_exit(void)
 {
        StructRNA *srna;
 
@@ -90,22 +98,19 @@ void RNA_exit()
 
 /* Pointer */
 
-PointerRNA PointerRNA_NULL = {{0}, 0, 0};
-
 void RNA_main_pointer_create(struct Main *main, PointerRNA *r_ptr)
 {
        r_ptr->id.data= NULL;
-       r_ptr->type= &RNA_Main;
+       r_ptr->type= &RNA_BlendData;
        r_ptr->data= main;
 }
 
 void RNA_id_pointer_create(ID *id, PointerRNA *r_ptr)
 {
-       PointerRNA tmp;
        StructRNA *type, *idtype= NULL;
 
        if(id) {
-               memset(&tmp, 0, sizeof(tmp));
+               PointerRNA tmp= {{NULL}};
                tmp.data= id;
                idtype= rna_ID_refine(&tmp);
                
@@ -126,14 +131,15 @@ void RNA_id_pointer_create(ID *id, PointerRNA *r_ptr)
 
 void RNA_pointer_create(ID *id, StructRNA *type, void *data, PointerRNA *r_ptr)
 {
-       PointerRNA tmp;
+#if 0 /* UNUSED */
        StructRNA *idtype= NULL;
 
        if(id) {
-               memset(&tmp, 0, sizeof(tmp));
+               PointerRNA tmp= {{0}};
                tmp.data= id;
                idtype= rna_ID_refine(&tmp);
        }
+#endif
 
        r_ptr->id.data= id;
        r_ptr->type= type;
@@ -170,9 +176,8 @@ void RNA_blender_rna_pointer_create(PointerRNA *r_ptr)
 
 PointerRNA rna_pointer_inherit_refine(PointerRNA *ptr, StructRNA *type, void *data)
 {
-       PointerRNA result;
-
        if(data) {
+               PointerRNA result;
                result.data= data;
                result.type= type;
                rna_pointer_inherit_id(type, ptr, &result);
@@ -185,11 +190,11 @@ PointerRNA rna_pointer_inherit_refine(PointerRNA *ptr, StructRNA *type, void *da
                        else
                                result.type= type;
                }
+               return result;
+       }
+       else {
+               return PointerRNA_NULL;
        }
-       else
-               memset(&result, 0, sizeof(result));
-       
-       return result;
 }
 
 /**/
@@ -235,13 +240,14 @@ IDProperty *rna_idproperty_ui(PropertyRNA *prop)
                }
        }
 
-       if (idprop)
-               return IDP_GetPropertyFromGroup(idprop, ((IDProperty *)prop)->name);
+       if (idprop) {
+               return IDP_GetPropertyTypeFromGroup(idprop, ((IDProperty *)prop)->name, IDP_GROUP);
+       }
 
        return NULL;
 }
 
-IDProperty *RNA_struct_idproperties(PointerRNA *ptr, int create)
+IDProperty *RNA_struct_idprops(PointerRNA *ptr, int create)
 {
        StructRNA *type= ptr->type;
 
@@ -251,22 +257,18 @@ IDProperty *RNA_struct_idproperties(PointerRNA *ptr, int create)
        return NULL;
 }
 
-int RNA_struct_idproperties_check(StructRNA *srna)
+int RNA_struct_idprops_check(StructRNA *srna)
 {
        return (srna && srna->idproperties) ? 1 : 0;
 }
 
 static IDProperty *rna_idproperty_find(PointerRNA *ptr, const char *name)
 {
-       IDProperty *group= RNA_struct_idproperties(ptr, 0);
-       IDProperty *idprop;
+       IDProperty *group= RNA_struct_idprops(ptr, 0);
+
+       if(group)
+               return IDP_GetPropertyFromGroup(group, name);
 
-       if(group) {
-               for(idprop=group->data.group.first; idprop; idprop=idprop->next)
-                       if(strcmp(idprop->name, name) == 0)
-                               return idprop;
-       }
-       
        return NULL;
 }
 
@@ -286,7 +288,7 @@ static int rna_ensure_property_array_length(PointerRNA *ptr, PropertyRNA *prop)
        }
 }
 
-static int rna_ensure_property_array_check(PointerRNA *ptr, PropertyRNA *prop)
+static int rna_ensure_property_array_check(PointerRNA *UNUSED(ptr), PropertyRNA *prop)
 {
        if(prop->magic == RNA_MAGIC) {
                return (prop->getlength || prop->totarraylength) ? 1:0;
@@ -363,19 +365,20 @@ static int rna_idproperty_verify_valid(PointerRNA *ptr, PropertyRNA *prop, IDPro
 }
 
 static PropertyRNA *typemap[IDP_NUMTYPES] =
-       {(PropertyRNA*)&rna_IDProperty_string,
-        (PropertyRNA*)&rna_IDProperty_int,
-        (PropertyRNA*)&rna_IDProperty_float,
+       {(PropertyRNA*)&rna_PropertyGroupItem_string,
+        (PropertyRNA*)&rna_PropertyGroupItem_int,
+        (PropertyRNA*)&rna_PropertyGroupItem_float,
         NULL, NULL, NULL,
-        (PropertyRNA*)&rna_IDProperty_group, NULL,
-        (PropertyRNA*)&rna_IDProperty_double};
+        (PropertyRNA*)&rna_PropertyGroupItem_group, NULL,
+        (PropertyRNA*)&rna_PropertyGroupItem_double,
+        (PropertyRNA*)&rna_PropertyGroupItem_idp_array};
 
 static PropertyRNA *arraytypemap[IDP_NUMTYPES] =
-       {NULL, (PropertyRNA*)&rna_IDProperty_int_array,
-        (PropertyRNA*)&rna_IDProperty_float_array,
+       {NULL, (PropertyRNA*)&rna_PropertyGroupItem_int_array,
+        (PropertyRNA*)&rna_PropertyGroupItem_float_array,
         NULL, NULL, NULL,
-        (PropertyRNA*)&rna_IDProperty_collection, NULL,
-        (PropertyRNA*)&rna_IDProperty_double_array};
+        (PropertyRNA*)&rna_PropertyGroupItem_collection, NULL,
+        (PropertyRNA*)&rna_PropertyGroupItem_double_array};
 
 IDProperty *rna_idproperty_check(PropertyRNA **prop, PointerRNA *ptr)
 {
@@ -391,7 +394,7 @@ IDProperty *rna_idproperty_check(PropertyRNA **prop, PointerRNA *ptr)
                        IDProperty *idprop= rna_idproperty_find(ptr, (*prop)->identifier);
 
                        if(idprop && !rna_idproperty_verify_valid(ptr, *prop, idprop)) {
-                               IDProperty *group= RNA_struct_idproperties(ptr, 0);
+                               IDProperty *group= RNA_struct_idprops(ptr, 0);
 
                                IDP_RemFromGroup(group, idprop);
                                IDP_FreeProperty(idprop);
@@ -450,11 +453,10 @@ static const char *rna_ensure_property_description(PropertyRNA *prop)
                /* attempt to get the local ID values */
                IDProperty *idp_ui= rna_idproperty_ui(prop);
 
-               if(idp_ui) { /* TODO, type checking on ID props */
-
-                       IDProperty *item= IDP_GetPropertyFromGroup(idp_ui, "description");
+               if(idp_ui) {
+                       IDProperty *item= IDP_GetPropertyTypeFromGroup(idp_ui, "description", IDP_STRING);
                        if(item)
-                               return (char *)item->data.pointer ;
+                               return IDP_String(item);
                }
 
                return ((IDProperty*)prop)->name; /* XXX - not correct */
@@ -514,6 +516,29 @@ int RNA_struct_is_ID(StructRNA *type)
        return (type->flag & STRUCT_ID) != 0;
 }
 
+int RNA_struct_idprops_register_check(StructRNA *type)
+{
+       return (type->flag & STRUCT_NO_IDPROPERTIES) == 0;
+}
+
+/* remove an id-property */
+int RNA_struct_idprops_unset(PointerRNA *ptr, const char *identifier)
+{
+       IDProperty *group= RNA_struct_idprops(ptr, 0);
+
+       if(group) {
+               IDProperty *idp= IDP_GetPropertyFromGroup(group, identifier);
+               if(idp) {
+                       IDP_RemFromGroup(group, idp);
+                       IDP_FreeProperty(idp);
+                       MEM_freeN(idp);
+
+                       return 1;
+               }
+       }
+       return 0;
+}
+
 int RNA_struct_is_a(StructRNA *type, StructRNA *srna)
 {
        StructRNA *base;
@@ -567,20 +592,48 @@ PropertyRNA *RNA_struct_find_nested(PointerRNA *ptr, StructRNA *srna)
        return prop;
 }
 
-const struct ListBase *RNA_struct_defined_properties(StructRNA *srna)
+int RNA_struct_contains_property(PointerRNA *ptr, PropertyRNA *prop_test)
+{
+       /* note, prop_test could be freed memory, only use for comparison */
+
+       /* validate the RNA is ok */
+       PropertyRNA *iterprop;
+       int found= FALSE;
+
+       iterprop= RNA_struct_iterator_property(ptr->type);
+
+       RNA_PROP_BEGIN(ptr, itemptr, iterprop) {
+               /* PropertyRNA *prop= itemptr.data; */
+               if(prop_test == (PropertyRNA *)itemptr.data) {
+                       found= TRUE;
+                       break;
+               }
+       }
+       RNA_PROP_END;
+
+       return found;
+}
+
+/* low level direct access to type->properties, note this ignores parent classes so should be used with care */
+const struct ListBase *RNA_struct_type_properties(StructRNA *srna)
 {
        return &srna->cont.properties;
 }
 
+PropertyRNA *RNA_struct_type_find_property(StructRNA *srna, const char *identifier)
+{
+       return BLI_findstring_ptr(&srna->cont.properties, identifier, offsetof(PropertyRNA, identifier));
+}
+
 FunctionRNA *RNA_struct_find_function(PointerRNA *ptr, const char *identifier)
 {
 #if 1
        FunctionRNA *func;
        StructRNA *type;
        for(type= ptr->type; type; type= type->base) {
-               for(func= type->functions.first; func; func= func->cont.next) {
-                       if(strcmp(func->identifier, identifier)==0)
-                               return func;
+               func= (FunctionRNA *)BLI_findstring_ptr(&type->functions, identifier, offsetof(FunctionRNA, identifier));
+               if(func) {
+                       return func;
                }
        }
        return NULL;
@@ -608,7 +661,7 @@ FunctionRNA *RNA_struct_find_function(PointerRNA *ptr, const char *identifier)
 #endif
 }
 
-const struct ListBase *RNA_struct_defined_functions(StructRNA *srna)
+const struct ListBase *RNA_struct_type_functions(StructRNA *srna)
 {
        return &srna->functions;
 }
@@ -628,6 +681,18 @@ StructUnregisterFunc RNA_struct_unregister(StructRNA *type)
        return NULL;
 }
 
+void **RNA_struct_instance(PointerRNA *ptr)
+{
+       StructRNA *type= ptr->type;
+
+       do {
+               if(type->instance)
+                       return type->instance(ptr);
+       } while((type=type->base));
+
+       return NULL;
+}
+
 void *RNA_struct_py_type_get(StructRNA *srna)
 {
        return srna->py_type;
@@ -690,6 +755,11 @@ int RNA_property_flag(PropertyRNA *prop)
        return rna_ensure_property(prop)->flag;
 }
 
+void *RNA_property_py_data_get(PropertyRNA *prop)
+{
+       return prop->py_data;
+}
+
 int RNA_property_array_length(PointerRNA *ptr, PropertyRNA *prop)
 {
        return rna_ensure_property_array_length(ptr, prop);
@@ -705,8 +775,8 @@ int RNA_property_array_dimension(PointerRNA *ptr, PropertyRNA *prop, int length[
 {
        PropertyRNA *rprop= rna_ensure_property(prop);
 
-       if(length && rprop->arraydimension > 1)
-               rna_ensure_property_multi_array_length(ptr, prop, length);
+       if(length)
+                       rna_ensure_property_multi_array_length(ptr, prop, length);
 
        return rprop->arraydimension;
 }
@@ -731,7 +801,7 @@ char RNA_property_array_item_char(PropertyRNA *prop, int index)
        /* get string to use for array index */
        if ((index < 4) && ELEM(subtype, PROP_QUATERNION, PROP_AXISANGLE))
                return quatitem[index];
-       else if((index < 4) && ELEM6(subtype, PROP_TRANSLATION, PROP_DIRECTION, PROP_XYZ, PROP_EULER, PROP_VELOCITY, PROP_ACCELERATION))
+       else if((index < 4) && ELEM8(subtype, PROP_TRANSLATION, PROP_DIRECTION, PROP_XYZ, PROP_XYZ_LENGTH, PROP_EULER, PROP_VELOCITY, PROP_ACCELERATION, PROP_COORDS))
                return vectoritem[index];
        else if ((index < 4) && ELEM(subtype, PROP_COLOR, PROP_COLOR_GAMMA))
                return coloritem[index];
@@ -743,43 +813,41 @@ int RNA_property_array_item_index(PropertyRNA *prop, char name)
 {
        PropertySubType subtype= rna_ensure_property(prop)->subtype;
 
-       name= toupper(name);
-
        /* get index based on string name/alias */
        /* maybe a function to find char index in string would be better than all the switches */
        if (ELEM(subtype, PROP_QUATERNION, PROP_AXISANGLE)) {
                switch (name) {
-                       case 'W':
+                       case 'w':
                                return 0;
-                       case 'X':
+                       case 'x':
                                return 1;
-                       case 'Y':
+                       case 'y':
                                return 2;
-                       case 'Z':
+                       case 'z':
                                return 3;
                }
        }
        else if(ELEM6(subtype, PROP_TRANSLATION, PROP_DIRECTION, PROP_XYZ, PROP_EULER, PROP_VELOCITY, PROP_ACCELERATION)) {
                switch (name) {
-                       case 'X':
+                       case 'x':
                                return 0;
-                       case 'Y':
+                       case 'y':
                                return 1;
-                       case 'Z':
+                       case 'z':
                                return 2;
-                       case 'W':
+                       case 'w':
                                return 3;
                }
        }
        else if (ELEM(subtype, PROP_COLOR, PROP_COLOR_GAMMA)) {
                switch (name) {
-                       case 'R':
+                       case 'r':
                                return 0;
-                       case 'G':
+                       case 'g':
                                return 1;
-                       case 'B':
+                       case 'b':
                                return 2;
-                       case 'A':
+                       case 'a':
                                return 3;
                }
        }
@@ -787,6 +855,7 @@ int RNA_property_array_item_index(PropertyRNA *prop, char name)
        return -1;
 }
 
+
 void RNA_property_int_range(PointerRNA *ptr, PropertyRNA *prop, int *hardmin, int *hardmax)
 {
        IntPropertyRNA *iprop= (IntPropertyRNA*)rna_ensure_property(prop);
@@ -794,14 +863,15 @@ void RNA_property_int_range(PointerRNA *ptr, PropertyRNA *prop, int *hardmin, in
        if(prop->magic != RNA_MAGIC) {
                /* attempt to get the local ID values */
                IDProperty *idp_ui= rna_idproperty_ui(prop);
-               IDProperty *item;
 
-               if(idp_ui) { /* TODO, type checking on ID props */
-                       item= IDP_GetPropertyFromGroup(idp_ui, "min");
-                       *hardmin= item ? item->data.val : INT_MIN;
+               if(idp_ui) {
+                       IDProperty *item;
+
+                       item= IDP_GetPropertyTypeFromGroup(idp_ui, "min", IDP_INT);
+                       *hardmin= item ? IDP_Int(item) : INT_MIN;
 
-                       item= IDP_GetPropertyFromGroup(idp_ui, "max");
-                       *hardmax= item ? item->data.val : INT_MAX;
+                       item= IDP_GetPropertyTypeFromGroup(idp_ui, "max", IDP_INT);
+                       *hardmax= item ? IDP_Int(item) : INT_MAX;
 
                        return;
                }
@@ -824,17 +894,18 @@ void RNA_property_int_ui_range(PointerRNA *ptr, PropertyRNA *prop, int *softmin,
        if(prop->magic != RNA_MAGIC) {
                /* attempt to get the local ID values */
                IDProperty *idp_ui= rna_idproperty_ui(prop);
-               IDProperty *item;
 
-               if(idp_ui) { /* TODO, type checking on ID props */
-                       item= IDP_GetPropertyFromGroup(idp_ui, "soft_min");
-                       *softmin= item ? item->data.val : INT_MIN;
+               if(idp_ui) {
+                       IDProperty *item;
+
+                       item= IDP_GetPropertyTypeFromGroup(idp_ui, "soft_min", IDP_INT);
+                       *softmin= item ? IDP_Int(item) : INT_MIN;
 
-                       item= IDP_GetPropertyFromGroup(idp_ui, "soft_max");
-                       *softmax= item ? item->data.val : INT_MAX;
+                       item= IDP_GetPropertyTypeFromGroup(idp_ui, "soft_max", IDP_INT);
+                       *softmax= item ? IDP_Int(item) : INT_MAX;
 
-                       item= IDP_GetPropertyFromGroup(idp_ui, "step");
-                       *step= item ? item->data.val : 1;
+                       item= IDP_GetPropertyTypeFromGroup(idp_ui, "step", IDP_INT);
+                       *step= item ? IDP_Int(item) : 1;
 
                        return;
                }
@@ -860,14 +931,15 @@ void RNA_property_float_range(PointerRNA *ptr, PropertyRNA *prop, float *hardmin
        if(prop->magic != RNA_MAGIC) {
                /* attempt to get the local ID values */
                IDProperty *idp_ui= rna_idproperty_ui(prop);
-               IDProperty *item;
 
-               if(idp_ui) { /* TODO, type checking on ID props */
-                       item= IDP_GetPropertyFromGroup(idp_ui, "min");
-                       *hardmin= item ? *(double*)&item->data.val : FLT_MIN;
+               if(idp_ui) {
+                       IDProperty *item;
+
+                       item= IDP_GetPropertyTypeFromGroup(idp_ui, "min", IDP_DOUBLE);
+                       *hardmin= item ? (float)IDP_Double(item) : FLT_MIN;
 
-                       item= IDP_GetPropertyFromGroup(idp_ui, "max");
-                       *hardmax= item ? *(double*)&item->data.val : FLT_MAX;
+                       item= IDP_GetPropertyTypeFromGroup(idp_ui, "max", IDP_DOUBLE);
+                       *hardmax= item ? (float)IDP_Double(item) : FLT_MAX;
 
                        return;
                }
@@ -890,20 +962,21 @@ void RNA_property_float_ui_range(PointerRNA *ptr, PropertyRNA *prop, float *soft
        if(prop->magic != RNA_MAGIC) {
                /* attempt to get the local ID values */
                IDProperty *idp_ui= rna_idproperty_ui(prop);
-               IDProperty *item;
 
-               if(idp_ui) { /* TODO, type checking on ID props */
-                       item= IDP_GetPropertyFromGroup(idp_ui, "soft_min");
-                       *softmin= item ? *(double*)&item->data.val : FLT_MIN;
+               if(idp_ui) {
+                       IDProperty *item;
+
+                       item= IDP_GetPropertyTypeFromGroup(idp_ui, "soft_min", IDP_DOUBLE);
+                       *softmin= item ? (float)IDP_Double(item) : FLT_MIN;
 
-                       item= IDP_GetPropertyFromGroup(idp_ui, "soft_max");
-                       *softmax= item ? *(double*)&item->data.val : FLT_MAX;
+                       item= IDP_GetPropertyTypeFromGroup(idp_ui, "soft_max", IDP_DOUBLE);
+                       *softmax= item ? (float)IDP_Double(item) : FLT_MAX;
 
-                       item= IDP_GetPropertyFromGroup(idp_ui, "step");
-                       *step= item ? *(double*)&item->data.val : 1.0f;
+                       item= IDP_GetPropertyTypeFromGroup(idp_ui, "step", IDP_DOUBLE);
+                       *step= item ? (float)IDP_Double(item) : 1.0f;
 
-                       item= IDP_GetPropertyFromGroup(idp_ui, "precision");
-                       *precision= item ? *(double*)&item->data.val : 3.0f;
+                       item= IDP_GetPropertyTypeFromGroup(idp_ui, "precision", IDP_DOUBLE);
+                       *precision= item ? (float)IDP_Double(item) : 3.0f;
 
                        return;
                }
@@ -961,7 +1034,8 @@ int RNA_property_int_clamp(PointerRNA *ptr, PropertyRNA *prop, int *value)
        }
 }
 
-/* this is the max length including \0 terminator */
+/* this is the max length including \0 terminator.
+ * '0' used when their is no maximum */
 int RNA_property_string_maxlength(PropertyRNA *prop)
 {
        StringPropertyRNA *sprop= (StringPropertyRNA*)rna_ensure_property(prop);
@@ -990,6 +1064,22 @@ StructRNA *RNA_property_pointer_type(PointerRNA *ptr, PropertyRNA *prop)
        return &RNA_UnknownType;
 }
 
+int RNA_property_pointer_poll(PointerRNA *ptr, PropertyRNA *prop, PointerRNA *value)
+{
+       prop= rna_ensure_property(prop);
+
+       if(prop->type == PROP_POINTER) {
+               PointerPropertyRNA *pprop= (PointerPropertyRNA*)prop;
+               if(pprop->poll)
+                       return pprop->poll(ptr, *value);
+
+               return 1;
+       }
+
+       printf("RNA_property_pointer_poll %s: is not a pointer property.\n", prop->identifier);
+       return 0;
+}
+
 /* Reuse for dynamic types  */
 EnumPropertyItem DummyRNA_NULL_items[] = {
        {0, NULL, 0, NULL, NULL}
@@ -1011,9 +1101,9 @@ void RNA_property_enum_items(bContext *C, PointerRNA *ptr, PropertyRNA *prop, En
                int tot= 0;
 
                if (prop->flag & PROP_ENUM_NO_CONTEXT)
-                       *item= eprop->itemf(NULL, ptr, free);
+                       *item= eprop->itemf(NULL, ptr, prop, free);
                else
-                       *item= eprop->itemf(C, ptr, free);
+                       *item= eprop->itemf(C, ptr, prop, free);
 
                if(totitem) {
                        if(*item) {
@@ -1034,21 +1124,26 @@ int RNA_property_enum_value(bContext *C, PointerRNA *ptr, PropertyRNA *prop, con
 {      
        EnumPropertyItem *item, *item_array;
        int free, found;
-       
+
        RNA_property_enum_items(C, ptr, prop, &item_array, NULL, &free);
-       
-       for(item= item_array; item->identifier; item++) {
-               if(item->identifier[0] && strcmp(item->identifier, identifier)==0) {
-                       *value = item->value;
-                       break;
+
+       if(item_array) {
+               for(item= item_array; item->identifier; item++) {
+                       if(item->identifier[0] && strcmp(item->identifier, identifier)==0) {
+                               *value = item->value;
+                               break;
+                       }
                }
-       }
-       
-       found= (item->identifier != NULL); /* could be alloc'd, assign before free */
 
-       if(free)
-               MEM_freeN(item_array);
+               found= (item->identifier != NULL); /* could be alloc'd, assign before free */
 
+               if(free) {
+                       MEM_freeN(item_array);
+               }
+       }
+       else {
+               found= 0;
+       }
        return found;
 }
 
@@ -1086,6 +1181,17 @@ int RNA_enum_name(EnumPropertyItem *item, const int value, const char **name)
        return 0;
 }
 
+int RNA_enum_description(EnumPropertyItem *item, const int value, const char **description)
+{
+       for (; item->identifier; item++) {
+               if(item->identifier[0] && item->value==value) {
+                       *description = item->description;
+                       return 1;
+               }
+       }
+       return 0;
+}
+
 int RNA_property_enum_identifier(bContext *C, PointerRNA *ptr, PropertyRNA *prop, const int value, const char **identifier)
 {      
        EnumPropertyItem *item= NULL;
@@ -1102,6 +1208,22 @@ int RNA_property_enum_identifier(bContext *C, PointerRNA *ptr, PropertyRNA *prop
        return 0;
 }
 
+int RNA_property_enum_name(bContext *C, PointerRNA *ptr, PropertyRNA *prop, const int value, const char **name)
+{      
+       EnumPropertyItem *item= NULL;
+       int result, free;
+       
+       RNA_property_enum_items(C, ptr, prop, &item, NULL, &free);
+       if(item) {
+               result= RNA_enum_name(item, value, name);
+               if(free)
+                       MEM_freeN(item);
+               
+               return result;
+       }
+       return 0;
+}
+
 int RNA_property_enum_bitflag_identifiers(bContext *C, PointerRNA *ptr, PropertyRNA *prop, const int value, const char **identifier)
 {
        EnumPropertyItem *item= NULL;
@@ -1187,13 +1309,36 @@ int RNA_property_animateable(PointerRNA *ptr, PropertyRNA *prop)
        return (prop->flag & PROP_EDITABLE);
 }
 
-int RNA_property_animated(PointerRNA *ptr, PropertyRNA *prop)
+int RNA_property_animated(PointerRNA *UNUSED(ptr), PropertyRNA *UNUSED(prop))
 {
        /* would need to ask animation system */
 
        return 0;
 }
 
+
+/* this function is to check if its possible to create a valid path from the ID
+ * its slow so dont call in a loop */
+int RNA_property_path_from_ID_check(PointerRNA *ptr, PropertyRNA *prop)
+{
+       char *path= RNA_path_from_ID_to_property(ptr, prop);
+       int ret= 0;
+
+       if(path) {
+               PointerRNA id_ptr;
+               PointerRNA r_ptr;
+               PropertyRNA *r_prop;
+
+               RNA_id_pointer_create(ptr->id.data, &id_ptr);
+               RNA_path_resolve(&id_ptr, path, &r_ptr, &r_prop);
+               ret= (prop == r_prop);
+               MEM_freeN(path);
+       }
+
+       return ret;
+}
+
+
 static void rna_property_update(bContext *C, Main *bmain, Scene *scene, PointerRNA *ptr, PropertyRNA *prop)
 {
        int is_rna = (prop->magic == RNA_MAGIC);
@@ -1204,7 +1349,14 @@ static void rna_property_update(bContext *C, Main *bmain, Scene *scene, PointerR
                        /* ideally no context would be needed for update, but there's some
                           parts of the code that need it still, so we have this exception */
                        if(prop->flag & PROP_CONTEXT_UPDATE) {
-                               if(C) ((ContextUpdateFunc)prop->update)(C, ptr);
+                               if(C) {
+                                       if(prop->flag & PROP_CONTEXT_PROPERTY_UPDATE) {
+                                               ((ContextPropUpdateFunc)prop->update)(C, ptr, prop);
+                                       }
+                                       else {
+                                               ((ContextUpdateFunc)prop->update)(C, ptr);
+                                       }
+                               }
                        }
                        else
                                prop->update(bmain, scene, ptr);
@@ -1215,12 +1367,20 @@ static void rna_property_update(bContext *C, Main *bmain, Scene *scene, PointerR
        else {
                /* WARNING! This is so property drivers update the display!
                 * not especially nice  */
-               DAG_id_flush_update(ptr->id.data, OB_RECALC);
+               DAG_id_tag_update(ptr->id.data, OB_RECALC_OB|OB_RECALC_DATA|OB_RECALC_TIME);
                WM_main_add_notifier(NC_WINDOW, NULL);
        }
 
 }
 
+/* must keep in sync with 'rna_property_update'
+ * note, its possible this returns a false positive in the case of PROP_CONTEXT_UPDATE
+ * but this isnt likely to be a performance problem. */
+int RNA_property_update_check(PropertyRNA *prop)
+{
+       return (prop->magic != RNA_MAGIC || prop->update || prop->noteflag);
+}
+
 void RNA_property_update(bContext *C, PointerRNA *ptr, PropertyRNA *prop)
 {
        rna_property_update(C, CTX_data_main(C), CTX_data_scene(C), ptr, prop);
@@ -1238,6 +1398,8 @@ int RNA_property_boolean_get(PointerRNA *ptr, PropertyRNA *prop)
        BooleanPropertyRNA *bprop= (BooleanPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_BOOLEAN);
+
        if((idprop=rna_idproperty_check(&prop, ptr)))
                return IDP_Int(idprop);
        else if(bprop->get)
@@ -1251,6 +1413,8 @@ void RNA_property_boolean_set(PointerRNA *ptr, PropertyRNA *prop, int value)
        BooleanPropertyRNA *bprop= (BooleanPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_BOOLEAN);
+
        /* just incase other values are passed */
        if(value) value= 1;
 
@@ -1264,7 +1428,7 @@ void RNA_property_boolean_set(PointerRNA *ptr, PropertyRNA *prop, int value)
 
                val.i= value;
 
-               group= RNA_struct_idproperties(ptr, 1);
+               group= RNA_struct_idprops(ptr, 1);
                if(group)
                        IDP_AddToGroup(group, IDP_New(IDP_INT, val, (char*)prop->identifier));
        }
@@ -1275,6 +1439,8 @@ void RNA_property_boolean_get_array(PointerRNA *ptr, PropertyRNA *prop, int *val
        BooleanPropertyRNA *bprop= (BooleanPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_BOOLEAN);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
                if(prop->arraydimension == 0)
                        values[0]= RNA_property_boolean_get(ptr, prop);
@@ -1296,6 +1462,8 @@ int RNA_property_boolean_get_index(PointerRNA *ptr, PropertyRNA *prop, int index
        int tmp[RNA_MAX_ARRAY_LENGTH];
        int len= rna_ensure_property_array_length(ptr, prop);
 
+       BLI_assert(RNA_property_type(prop) == PROP_BOOLEAN);
+
        if(len <= RNA_MAX_ARRAY_LENGTH) {
                RNA_property_boolean_get_array(ptr, prop, tmp);
                return tmp[index];
@@ -1317,6 +1485,8 @@ void RNA_property_boolean_set_array(PointerRNA *ptr, PropertyRNA *prop, const in
        BooleanPropertyRNA *bprop= (BooleanPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_BOOLEAN);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
                if(prop->arraydimension == 0)
                        IDP_Int(idprop)= values[0];
@@ -1334,7 +1504,7 @@ void RNA_property_boolean_set_array(PointerRNA *ptr, PropertyRNA *prop, const in
                val.array.len= prop->totarraylength;
                val.array.type= IDP_INT;
 
-               group= RNA_struct_idproperties(ptr, 1);
+               group= RNA_struct_idprops(ptr, 1);
                if(group) {
                        idprop= IDP_New(IDP_ARRAY, val, (char*)prop->identifier);
                        IDP_AddToGroup(group, idprop);
@@ -1348,6 +1518,8 @@ void RNA_property_boolean_set_index(PointerRNA *ptr, PropertyRNA *prop, int inde
        int tmp[RNA_MAX_ARRAY_LENGTH];
        int len= rna_ensure_property_array_length(ptr, prop);
 
+       BLI_assert(RNA_property_type(prop) == PROP_BOOLEAN);
+
        if(len <= RNA_MAX_ARRAY_LENGTH) {
                RNA_property_boolean_get_array(ptr, prop, tmp);
                tmp[index]= value;
@@ -1364,16 +1536,21 @@ void RNA_property_boolean_set_index(PointerRNA *ptr, PropertyRNA *prop, int inde
        }
 }
 
-int RNA_property_boolean_get_default(PointerRNA *ptr, PropertyRNA *prop)
+int RNA_property_boolean_get_default(PointerRNA *UNUSED(ptr), PropertyRNA *prop)
 {
        BooleanPropertyRNA *bprop= (BooleanPropertyRNA*)prop;
+
+       BLI_assert(RNA_property_type(prop) == PROP_BOOLEAN);
+
        return bprop->defaultvalue;
 }
 
-void RNA_property_boolean_get_default_array(PointerRNA *ptr, PropertyRNA *prop, int *values)
+void RNA_property_boolean_get_default_array(PointerRNA *UNUSED(ptr), PropertyRNA *prop, int *values)
 {
        BooleanPropertyRNA *bprop= (BooleanPropertyRNA*)prop;
        
+       BLI_assert(RNA_property_type(prop) == PROP_BOOLEAN);
+
        if(prop->arraydimension == 0)
                values[0]= bprop->defaultvalue;
        else if(bprop->defaultarray)
@@ -1387,6 +1564,8 @@ int RNA_property_boolean_get_default_index(PointerRNA *ptr, PropertyRNA *prop, i
        int tmp[RNA_MAX_ARRAY_LENGTH];
        int len= rna_ensure_property_array_length(ptr, prop);
 
+       BLI_assert(RNA_property_type(prop) == PROP_BOOLEAN);
+
        if(len <= RNA_MAX_ARRAY_LENGTH) {
                RNA_property_boolean_get_default_array(ptr, prop, tmp);
                return tmp[index];
@@ -1408,6 +1587,8 @@ int RNA_property_int_get(PointerRNA *ptr, PropertyRNA *prop)
        IntPropertyRNA *iprop= (IntPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_INT);
+
        if((idprop=rna_idproperty_check(&prop, ptr)))
                return IDP_Int(idprop);
        else if(iprop->get)
@@ -1421,6 +1602,8 @@ void RNA_property_int_set(PointerRNA *ptr, PropertyRNA *prop, int value)
        IntPropertyRNA *iprop= (IntPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_INT);
+
        if((idprop=rna_idproperty_check(&prop, ptr)))
                IDP_Int(idprop)= value;
        else if(iprop->set)
@@ -1431,7 +1614,7 @@ void RNA_property_int_set(PointerRNA *ptr, PropertyRNA *prop, int value)
 
                val.i= value;
 
-               group= RNA_struct_idproperties(ptr, 1);
+               group= RNA_struct_idprops(ptr, 1);
                if(group)
                        IDP_AddToGroup(group, IDP_New(IDP_INT, val, (char*)prop->identifier));
        }
@@ -1442,6 +1625,8 @@ void RNA_property_int_get_array(PointerRNA *ptr, PropertyRNA *prop, int *values)
        IntPropertyRNA *iprop= (IntPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_INT);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
                if(prop->arraydimension == 0)
                        values[0]= RNA_property_int_get(ptr, prop);
@@ -1458,11 +1643,50 @@ void RNA_property_int_get_array(PointerRNA *ptr, PropertyRNA *prop, int *values)
                memset(values, 0, sizeof(int)*prop->totarraylength);
 }
 
+void RNA_property_int_get_array_range(PointerRNA *ptr, PropertyRNA *prop, int values[2])
+{
+       const int array_len= RNA_property_array_length(ptr, prop);
+
+       if(array_len <= 0) {
+               values[0]= 0;
+               values[1]= 0;
+       }
+       else if (array_len == 1) {
+               RNA_property_int_get_array(ptr, prop, values);
+               values[1]= values[0];
+       }
+       else {
+               int arr_stack[32];
+               int *arr;
+               int i;
+
+               if(array_len > 32) {
+                       arr= MEM_mallocN(sizeof(int) * array_len, "RNA_property_int_get_array_range");
+               }
+               else {
+                       arr= arr_stack;
+               }
+
+               RNA_property_int_get_array(ptr, prop, arr);
+               values[0]= values[1]= arr[0];
+               for(i= 1; i < array_len; i++) {
+                       values[0]= MIN2(values[0], arr[i]);
+                       values[1]= MAX2(values[1], arr[i]);
+               }
+
+               if(arr != arr_stack) {
+                       MEM_freeN(arr);
+               }
+       }
+}
+
 int RNA_property_int_get_index(PointerRNA *ptr, PropertyRNA *prop, int index)
 {
        int tmp[RNA_MAX_ARRAY_LENGTH];
        int len= rna_ensure_property_array_length(ptr, prop);
 
+       BLI_assert(RNA_property_type(prop) == PROP_INT);
+
        if(len <= RNA_MAX_ARRAY_LENGTH) {
                RNA_property_int_get_array(ptr, prop, tmp);
                return tmp[index];
@@ -1484,6 +1708,8 @@ void RNA_property_int_set_array(PointerRNA *ptr, PropertyRNA *prop, const int *v
        IntPropertyRNA *iprop= (IntPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_INT);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
                if(prop->arraydimension == 0)
                        IDP_Int(idprop)= values[0];
@@ -1501,7 +1727,7 @@ void RNA_property_int_set_array(PointerRNA *ptr, PropertyRNA *prop, const int *v
                val.array.len= prop->totarraylength;
                val.array.type= IDP_INT;
 
-               group= RNA_struct_idproperties(ptr, 1);
+               group= RNA_struct_idprops(ptr, 1);
                if(group) {
                        idprop= IDP_New(IDP_ARRAY, val, (char*)prop->identifier);
                        IDP_AddToGroup(group, idprop);
@@ -1515,6 +1741,8 @@ void RNA_property_int_set_index(PointerRNA *ptr, PropertyRNA *prop, int index, i
        int tmp[RNA_MAX_ARRAY_LENGTH];
        int len= rna_ensure_property_array_length(ptr, prop);
 
+       BLI_assert(RNA_property_type(prop) == PROP_INT);
+
        if(len <= RNA_MAX_ARRAY_LENGTH) {
                RNA_property_int_get_array(ptr, prop, tmp);
                tmp[index]= value;
@@ -1531,16 +1759,18 @@ void RNA_property_int_set_index(PointerRNA *ptr, PropertyRNA *prop, int index, i
        }
 }
 
-int RNA_property_int_get_default(PointerRNA *ptr, PropertyRNA *prop)
+int RNA_property_int_get_default(PointerRNA *UNUSED(ptr), PropertyRNA *prop)
 {
        IntPropertyRNA *iprop= (IntPropertyRNA*)prop;
        return iprop->defaultvalue;
 }
 
-void RNA_property_int_get_default_array(PointerRNA *ptr, PropertyRNA *prop, int *values)
+void RNA_property_int_get_default_array(PointerRNA *UNUSED(ptr), PropertyRNA *prop, int *values)
 {
        IntPropertyRNA *iprop= (IntPropertyRNA*)prop;
        
+       BLI_assert(RNA_property_type(prop) == PROP_INT);
+
        if(prop->arraydimension == 0)
                values[0]= iprop->defaultvalue;
        else if(iprop->defaultarray)
@@ -1575,6 +1805,8 @@ float RNA_property_float_get(PointerRNA *ptr, PropertyRNA *prop)
        FloatPropertyRNA *fprop= (FloatPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_FLOAT);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
                if(idprop->type == IDP_FLOAT)
                        return IDP_Float(idprop);
@@ -1592,6 +1824,8 @@ void RNA_property_float_set(PointerRNA *ptr, PropertyRNA *prop, float value)
        FloatPropertyRNA *fprop= (FloatPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_FLOAT);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
                if(idprop->type == IDP_FLOAT)
                        IDP_Float(idprop)= value;
@@ -1607,7 +1841,7 @@ void RNA_property_float_set(PointerRNA *ptr, PropertyRNA *prop, float value)
 
                val.f= value;
 
-               group= RNA_struct_idproperties(ptr, 1);
+               group= RNA_struct_idprops(ptr, 1);
                if(group)
                        IDP_AddToGroup(group, IDP_New(IDP_FLOAT, val, (char*)prop->identifier));
        }
@@ -1619,6 +1853,8 @@ void RNA_property_float_get_array(PointerRNA *ptr, PropertyRNA *prop, float *val
        IDProperty *idprop;
        int i;
 
+       BLI_assert(RNA_property_type(prop) == PROP_FLOAT);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
                if(prop->arraydimension == 0)
                        values[0]= RNA_property_float_get(ptr, prop);
@@ -1640,11 +1876,50 @@ void RNA_property_float_get_array(PointerRNA *ptr, PropertyRNA *prop, float *val
                memset(values, 0, sizeof(float)*prop->totarraylength);
 }
 
+void RNA_property_float_get_array_range(PointerRNA *ptr, PropertyRNA *prop, float values[2])
+{
+       const int array_len= RNA_property_array_length(ptr, prop);
+
+       if(array_len <= 0) {
+               values[0]= 0.0f;
+               values[1]= 0.0f;
+       }
+       else if (array_len == 1) {
+               RNA_property_float_get_array(ptr, prop, values);
+               values[1]= values[0];
+       }
+       else {
+               float arr_stack[32];
+               float *arr;
+               int i;
+
+               if(array_len > 32) {
+                       arr= MEM_mallocN(sizeof(float) * array_len, "RNA_property_float_get_array_range");
+               }
+               else {
+                       arr= arr_stack;
+               }
+
+               RNA_property_float_get_array(ptr, prop, arr);
+               values[0]= values[1]= arr[0];
+               for(i= 1; i < array_len; i++) {
+                       values[0]= MIN2(values[0], arr[i]);
+                       values[1]= MAX2(values[1], arr[i]);
+               }
+
+               if(arr != arr_stack) {
+                       MEM_freeN(arr);
+               }
+       }
+}
+
 float RNA_property_float_get_index(PointerRNA *ptr, PropertyRNA *prop, int index)
 {
        float tmp[RNA_MAX_ARRAY_LENGTH];
        int len= rna_ensure_property_array_length(ptr, prop);
 
+       BLI_assert(RNA_property_type(prop) == PROP_FLOAT);
+
        if(len <= RNA_MAX_ARRAY_LENGTH) {
                RNA_property_float_get_array(ptr, prop, tmp);
                return tmp[index];
@@ -1668,6 +1943,8 @@ void RNA_property_float_set_array(PointerRNA *ptr, PropertyRNA *prop, const floa
        IDProperty *idprop;
        int i;
 
+       BLI_assert(RNA_property_type(prop) == PROP_FLOAT);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
                if(prop->arraydimension == 0) {
                        if(idprop->type == IDP_FLOAT)
@@ -1695,7 +1972,7 @@ void RNA_property_float_set_array(PointerRNA *ptr, PropertyRNA *prop, const floa
                val.array.len= prop->totarraylength;
                val.array.type= IDP_FLOAT;
 
-               group= RNA_struct_idproperties(ptr, 1);
+               group= RNA_struct_idprops(ptr, 1);
                if(group) {
                        idprop= IDP_New(IDP_ARRAY, val, (char*)prop->identifier);
                        IDP_AddToGroup(group, idprop);
@@ -1709,6 +1986,8 @@ void RNA_property_float_set_index(PointerRNA *ptr, PropertyRNA *prop, int index,
        float tmp[RNA_MAX_ARRAY_LENGTH];
        int len= rna_ensure_property_array_length(ptr, prop);
 
+       BLI_assert(RNA_property_type(prop) == PROP_FLOAT);
+
        if(len <= RNA_MAX_ARRAY_LENGTH) {
                RNA_property_float_get_array(ptr, prop, tmp);
                tmp[index]= value;
@@ -1725,16 +2004,21 @@ void RNA_property_float_set_index(PointerRNA *ptr, PropertyRNA *prop, int index,
        }
 }
 
-float RNA_property_float_get_default(PointerRNA *ptr, PropertyRNA *prop)
+float RNA_property_float_get_default(PointerRNA *UNUSED(ptr), PropertyRNA *prop)
 {
        FloatPropertyRNA *fprop= (FloatPropertyRNA*)prop;
+
+       BLI_assert(RNA_property_type(prop) == PROP_FLOAT);
+
        return fprop->defaultvalue;
 }
 
-void RNA_property_float_get_default_array(PointerRNA *ptr, PropertyRNA *prop, float *values)
+void RNA_property_float_get_default_array(PointerRNA *UNUSED(ptr), PropertyRNA *prop, float *values)
 {
        FloatPropertyRNA *fprop= (FloatPropertyRNA*)prop;
        
+       BLI_assert(RNA_property_type(prop) == PROP_FLOAT);
+
        if(prop->arraydimension == 0)
                values[0]= fprop->defaultvalue;
        else if(fprop->defaultarray)
@@ -1748,6 +2032,8 @@ float RNA_property_float_get_default_index(PointerRNA *ptr, PropertyRNA *prop, i
        float tmp[RNA_MAX_ARRAY_LENGTH];
        int len= rna_ensure_property_array_length(ptr, prop);
 
+       BLI_assert(RNA_property_type(prop) == PROP_FLOAT);
+
        if(len <= RNA_MAX_ARRAY_LENGTH) {
                RNA_property_float_get_default_array(ptr, prop, tmp);
                return tmp[index];
@@ -1769,6 +2055,8 @@ void RNA_property_string_get(PointerRNA *ptr, PropertyRNA *prop, char *value)
        StringPropertyRNA *sprop= (StringPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_STRING);
+
        if((idprop=rna_idproperty_check(&prop, ptr)))
                strcpy(value, IDP_String(idprop));
        else if(sprop->get)
@@ -1782,6 +2070,8 @@ char *RNA_property_string_get_alloc(PointerRNA *ptr, PropertyRNA *prop, char *fi
        char *buf;
        int length;
 
+       BLI_assert(RNA_property_type(prop) == PROP_STRING);
+
        length= RNA_property_string_length(ptr, prop);
 
        if(length+1 < fixedlen)
@@ -1800,6 +2090,8 @@ int RNA_property_string_length(PointerRNA *ptr, PropertyRNA *prop)
        StringPropertyRNA *sprop= (StringPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_STRING);
+
        if((idprop=rna_idproperty_check(&prop, ptr)))
                return strlen(IDP_String(idprop));
        else if(sprop->length)
@@ -1813,25 +2105,27 @@ void RNA_property_string_set(PointerRNA *ptr, PropertyRNA *prop, const char *val
        StringPropertyRNA *sprop= (StringPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_STRING);
+
        if((idprop=rna_idproperty_check(&prop, ptr)))
-               IDP_AssignString(idprop, (char*)value);
+               IDP_AssignString(idprop, (char*)value, RNA_property_string_maxlength(prop) - 1);
        else if(sprop->set)
-               sprop->set(ptr, value);
+               sprop->set(ptr, value); /* set function needs to clamp its self */
        else if(prop->flag & PROP_EDITABLE) {
-               IDPropertyTemplate val = {0};
                IDProperty *group;
 
-               val.str= (char*)value;
-
-               group= RNA_struct_idproperties(ptr, 1);
+               group= RNA_struct_idprops(ptr, 1);
                if(group)
-                       IDP_AddToGroup(group, IDP_New(IDP_STRING, val, (char*)prop->identifier));
+                       IDP_AddToGroup(group, IDP_NewString((char*)value, (char*)prop->identifier, RNA_property_string_maxlength(prop) - 1));
        }
 }
 
-void RNA_property_string_get_default(PointerRNA *ptr, PropertyRNA *prop, char *value)
+void RNA_property_string_get_default(PointerRNA *UNUSED(ptr), PropertyRNA *prop, char *value)
 {
        StringPropertyRNA *sprop= (StringPropertyRNA*)prop;
+
+       BLI_assert(RNA_property_type(prop) == PROP_STRING);
+
        strcpy(value, sprop->defaultvalue);
 }
 
@@ -1840,6 +2134,8 @@ char *RNA_property_string_get_default_alloc(PointerRNA *ptr, PropertyRNA *prop,
        char *buf;
        int length;
 
+       BLI_assert(RNA_property_type(prop) == PROP_STRING);
+
        length= RNA_property_string_default_length(ptr, prop);
 
        if(length+1 < fixedlen)
@@ -1853,9 +2149,12 @@ char *RNA_property_string_get_default_alloc(PointerRNA *ptr, PropertyRNA *prop,
 }
 
 /* this is the length without \0 terminator */
-int RNA_property_string_default_length(PointerRNA *ptr, PropertyRNA *prop)
+int RNA_property_string_default_length(PointerRNA *UNUSED(ptr), PropertyRNA *prop)
 {
        StringPropertyRNA *sprop= (StringPropertyRNA*)prop;
+
+       BLI_assert(RNA_property_type(prop) == PROP_STRING);
+
        return strlen(sprop->defaultvalue);
 }
 
@@ -1864,6 +2163,8 @@ int RNA_property_enum_get(PointerRNA *ptr, PropertyRNA *prop)
        EnumPropertyRNA *eprop= (EnumPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_ENUM);
+
        if((idprop=rna_idproperty_check(&prop, ptr)))
                return IDP_Int(idprop);
        else if(eprop->get)
@@ -1877,6 +2178,8 @@ void RNA_property_enum_set(PointerRNA *ptr, PropertyRNA *prop, int value)
        EnumPropertyRNA *eprop= (EnumPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_ENUM);
+
        if((idprop=rna_idproperty_check(&prop, ptr)))
                IDP_Int(idprop)= value;
        else if(eprop->set) {
@@ -1888,24 +2191,37 @@ void RNA_property_enum_set(PointerRNA *ptr, PropertyRNA *prop, int value)
 
                val.i= value;
 
-               group= RNA_struct_idproperties(ptr, 1);
+               group= RNA_struct_idprops(ptr, 1);
                if(group)
                        IDP_AddToGroup(group, IDP_New(IDP_INT, val, (char*)prop->identifier));
        }
 }
 
-int RNA_property_enum_get_default(PointerRNA *ptr, PropertyRNA *prop)
+int RNA_property_enum_get_default(PointerRNA *UNUSED(ptr), PropertyRNA *prop)
 {
        EnumPropertyRNA *eprop= (EnumPropertyRNA*)prop;
+
+       BLI_assert(RNA_property_type(prop) == PROP_ENUM);
+
        return eprop->defaultvalue;
 }
 
+void *RNA_property_enum_py_data_get(PropertyRNA *prop)
+{
+       EnumPropertyRNA *eprop= (EnumPropertyRNA*)prop;
+
+       BLI_assert(RNA_property_type(prop) == PROP_ENUM);
+
+       return eprop->py_data;
+}
 
 PointerRNA RNA_property_pointer_get(PointerRNA *ptr, PropertyRNA *prop)
 {
        PointerPropertyRNA *pprop= (PointerPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_POINTER);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
                pprop= (PointerPropertyRNA*)prop;
 
@@ -1922,18 +2238,17 @@ PointerRNA RNA_property_pointer_get(PointerRNA *ptr, PropertyRNA *prop)
                return RNA_property_pointer_get(ptr, prop);
        }
        else {
-               PointerRNA result;
-
-               memset(&result, 0, sizeof(result));
-               return result;
+               return PointerRNA_NULL;
        }
 }
 
 void RNA_property_pointer_set(PointerRNA *ptr, PropertyRNA *prop, PointerRNA ptr_value)
 {
-       IDProperty *idprop;
+       /*IDProperty *idprop;*/
 
-       if((idprop=rna_idproperty_check(&prop, ptr))) {
+       BLI_assert(RNA_property_type(prop) == PROP_POINTER);
+
+       if((/*idprop=*/ rna_idproperty_check(&prop, ptr))) {
                /* not supported */
        }
        else {
@@ -1948,11 +2263,22 @@ void RNA_property_pointer_set(PointerRNA *ptr, PropertyRNA *prop, PointerRNA ptr
        }
 }
 
+PointerRNA RNA_property_pointer_get_default(PointerRNA *UNUSED(ptr), PropertyRNA *UNUSED(prop))
+{
+       //PointerPropertyRNA *pprop= (PointerPropertyRNA*)prop;
+
+       // BLI_assert(RNA_property_type(prop) == PROP_POINTER);
+
+       return PointerRNA_NULL; // FIXME: there has to be a way...
+}
+
 void RNA_property_pointer_add(PointerRNA *ptr, PropertyRNA *prop)
 {
-       IDProperty *idprop;
+       /*IDProperty *idprop;*/
 
-       if((idprop=rna_idproperty_check(&prop, ptr))) {
+       BLI_assert(RNA_property_type(prop) == PROP_POINTER);
+
+       if((/*idprop=*/rna_idproperty_check(&prop, ptr))) {
                /* already exists */
        }
        else if(prop->flag & PROP_IDPROPERTY) {
@@ -1961,7 +2287,7 @@ void RNA_property_pointer_add(PointerRNA *ptr, PropertyRNA *prop)
 
                val.i= 0;
 
-               group= RNA_struct_idproperties(ptr, 1);
+               group= RNA_struct_idprops(ptr, 1);
                if(group)
                        IDP_AddToGroup(group, IDP_New(IDP_GROUP, val, (char*)prop->identifier));
        }
@@ -1973,8 +2299,10 @@ void RNA_property_pointer_remove(PointerRNA *ptr, PropertyRNA *prop)
 {
        IDProperty *idprop, *group;
 
+       BLI_assert(RNA_property_type(prop) == PROP_POINTER);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
-               group= RNA_struct_idproperties(ptr, 0);
+               group= RNA_struct_idprops(ptr, 0);
                
                if(group) {
                        IDP_RemFromGroup(group, idprop);
@@ -1999,6 +2327,8 @@ void RNA_property_collection_begin(PointerRNA *ptr, PropertyRNA *prop, Collectio
 {
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_COLLECTION);
+
        memset(iter, 0, sizeof(*iter));
 
        if((idprop=rna_idproperty_check(&prop, ptr)) || (prop->flag & PROP_IDPROPERTY)) {
@@ -2023,7 +2353,7 @@ void RNA_property_collection_begin(PointerRNA *ptr, PropertyRNA *prop, Collectio
 
 void RNA_property_collection_next(CollectionPropertyIterator *iter)
 {
-       CollectionPropertyRNA *cprop= (CollectionPropertyRNA*)iter->prop;
+       CollectionPropertyRNA *cprop= (CollectionPropertyRNA*)rna_ensure_property(iter->prop);
 
        if(iter->idprop) {
                rna_iterator_array_next(iter);
@@ -2037,7 +2367,7 @@ void RNA_property_collection_next(CollectionPropertyIterator *iter)
 
 void RNA_property_collection_end(CollectionPropertyIterator *iter)
 {
-       CollectionPropertyRNA *cprop= (CollectionPropertyRNA*)iter->prop;
+       CollectionPropertyRNA *cprop= (CollectionPropertyRNA*)rna_ensure_property(iter->prop);
 
        if(iter->idprop)
                rna_iterator_array_end(iter);
@@ -2050,6 +2380,8 @@ int RNA_property_collection_length(PointerRNA *ptr, PropertyRNA *prop)
        CollectionPropertyRNA *cprop= (CollectionPropertyRNA*)prop;
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_COLLECTION);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
                return idprop->len;
        }
@@ -2074,6 +2406,8 @@ void RNA_property_collection_add(PointerRNA *ptr, PropertyRNA *prop, PointerRNA
        IDProperty *idprop;
 //     CollectionPropertyRNA *cprop= (CollectionPropertyRNA*)prop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_COLLECTION);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
                IDPropertyTemplate val = {0};
                IDProperty *item;
@@ -2087,7 +2421,7 @@ void RNA_property_collection_add(PointerRNA *ptr, PropertyRNA *prop, PointerRNA
                IDProperty *group, *item;
                IDPropertyTemplate val = {0};
 
-               group= RNA_struct_idproperties(ptr, 1);
+               group= RNA_struct_idprops(ptr, 1);
                if(group) {
                        idprop= IDP_NewIDPArray(prop->identifier);
                        IDP_AddToGroup(group, idprop);
@@ -2131,6 +2465,8 @@ int RNA_property_collection_remove(PointerRNA *ptr, PropertyRNA *prop, int key)
        IDProperty *idprop;
 //     CollectionPropertyRNA *cprop= (CollectionPropertyRNA*)prop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_COLLECTION);
+
        if((idprop=rna_idproperty_check(&prop, ptr))) {
                IDProperty tmp, *array;
                int len;
@@ -2172,10 +2508,42 @@ int RNA_property_collection_remove(PointerRNA *ptr, PropertyRNA *prop, int key)
        return 0;
 }
 
+int RNA_property_collection_move(PointerRNA *ptr, PropertyRNA *prop, int key, int pos)
+{
+       IDProperty *idprop;
+
+       BLI_assert(RNA_property_type(prop) == PROP_COLLECTION);
+
+       if((idprop=rna_idproperty_check(&prop, ptr))) {
+               IDProperty tmp, *array;
+               int len;
+
+               len= idprop->len;
+               array= IDP_IDPArray(idprop);
+
+               if(key >= 0 && key < len && pos >= 0 && pos < len && key != pos) {
+                       memcpy(&tmp, &array[key], sizeof(IDProperty));
+                       if(pos < key)
+                               memmove(array+pos+1, array+pos, sizeof(IDProperty)*(key - pos));
+                       else
+                               memmove(array+key, array+key+1, sizeof(IDProperty)*(pos - key));
+                       memcpy(&array[pos], &tmp, sizeof(IDProperty));
+               }
+
+               return 1;
+       }
+       else if(prop->flag & PROP_IDPROPERTY)
+               return 1;
+
+       return 0;
+}
+
 void RNA_property_collection_clear(PointerRNA *ptr, PropertyRNA *prop)
 {
        IDProperty *idprop;
 
+       BLI_assert(RNA_property_type(prop) == PROP_COLLECTION);
+
        if((idprop=rna_idproperty_check(&prop, ptr)))
                IDP_ResizeIDPArray(idprop, 0);
 }
@@ -2185,6 +2553,8 @@ int RNA_property_collection_lookup_index(PointerRNA *ptr, PropertyRNA *prop, Poi
        CollectionPropertyIterator iter;
        int index= 0;
        
+       BLI_assert(RNA_property_type(prop) == PROP_COLLECTION);
+
        RNA_property_collection_begin(ptr, prop, &iter);
        for(index=0; iter.valid; RNA_property_collection_next(&iter), index++) {
                if (iter.ptr.data == t_ptr->data)
@@ -2201,12 +2571,13 @@ int RNA_property_collection_lookup_index(PointerRNA *ptr, PropertyRNA *prop, Poi
 
 int RNA_property_collection_lookup_int(PointerRNA *ptr, PropertyRNA *prop, int key, PointerRNA *r_ptr)
 {
-       CollectionPropertyRNA *cprop= (CollectionPropertyRNA*)prop;
+       CollectionPropertyRNA *cprop= (CollectionPropertyRNA*)rna_ensure_property(prop);
+
+       BLI_assert(RNA_property_type(prop) == PROP_COLLECTION);
 
        if(cprop->lookupint) {
                /* we have a callback defined, use it */
-               *r_ptr= cprop->lookupint(ptr, key);
-               return (r_ptr->data != NULL);
+               return cprop->lookupint(ptr, key, r_ptr);
        }
        else {
                /* no callback defined, just iterate and find the nth item */
@@ -2231,12 +2602,13 @@ int RNA_property_collection_lookup_int(PointerRNA *ptr, PropertyRNA *prop, int k
 
 int RNA_property_collection_lookup_string(PointerRNA *ptr, PropertyRNA *prop, const char *key, PointerRNA *r_ptr)
 {
-       CollectionPropertyRNA *cprop= (CollectionPropertyRNA*)prop;
+       CollectionPropertyRNA *cprop= (CollectionPropertyRNA*)rna_ensure_property(prop);
+
+       BLI_assert(RNA_property_type(prop) == PROP_COLLECTION);
 
        if(cprop->lookupstring) {
                /* we have a callback defined, use it */
-               *r_ptr= cprop->lookupstring(ptr, key);
-               return (r_ptr->data != NULL);
+               return cprop->lookupstring(ptr, key, r_ptr);
        }
        else {
                /* no callback defined, compare with name properties if they exist */
@@ -2275,6 +2647,8 @@ int RNA_property_collection_lookup_string(PointerRNA *ptr, PropertyRNA *prop, co
 
 int RNA_property_collection_type_get(PointerRNA *ptr, PropertyRNA *prop, PointerRNA *r_ptr)
 {
+       BLI_assert(RNA_property_type(prop) == PROP_COLLECTION);
+
        *r_ptr= *ptr;
        return ((r_ptr->type = prop->srna) ? 1:0);
 }
@@ -2285,6 +2659,8 @@ int RNA_property_collection_raw_array(PointerRNA *ptr, PropertyRNA *prop, Proper
        ArrayIterator *internal;
        char *arrayp;
 
+       BLI_assert(RNA_property_type(prop) == PROP_COLLECTION);
+
        if(!(prop->flag & PROP_RAW_ARRAY) || !(itemprop->flag & PROP_RAW_ACCESS))
                return 0;
 
@@ -2350,7 +2726,7 @@ int RNA_raw_type_sizeof(RawPropertyType type)
        }
 }
 
-static int rna_raw_access(ReportList *reports, PointerRNA *ptr, PropertyRNA *prop, char *propname, void *inarray, RawPropertyType intype, int inlen, int set)
+static int rna_raw_access(ReportList *reports, PointerRNA *ptr, PropertyRNA *prop, const char *propname, void *inarray, RawPropertyType intype, int inlen, int set)
 {
        StructRNA *ptype;
        PointerRNA itemptr;
@@ -2652,12 +3028,12 @@ RawPropertyType RNA_property_raw_type(PropertyRNA *prop)
        return prop->rawtype;
 }
 
-int RNA_property_collection_raw_get(ReportList *reports, PointerRNA *ptr, PropertyRNA *prop, char *propname, void *array, RawPropertyType type, int len)
+int RNA_property_collection_raw_get(ReportList *reports, PointerRNA *ptr, PropertyRNA *prop, const char *propname, void *array, RawPropertyType type, int len)
 {
        return rna_raw_access(reports, ptr, prop, propname, array, type, len, 0);
 }
 
-int RNA_property_collection_raw_set(ReportList *reports, PointerRNA *ptr, PropertyRNA *prop, char *propname, void *array, RawPropertyType type, int len)
+int RNA_property_collection_raw_set(ReportList *reports, PointerRNA *ptr, PropertyRNA *prop, const char *propname, void *array, RawPropertyType type, int len)
 {
        return rna_raw_access(reports, ptr, prop, propname, array, type, len, 1);
 }
@@ -2708,12 +3084,22 @@ void rna_iterator_listbase_end(CollectionPropertyIterator *iter)
        iter->internal= NULL;
 }
 
+PointerRNA rna_listbase_lookup_int(PointerRNA *ptr, StructRNA *type, struct ListBase *lb, int index)
+{
+       void *data= BLI_findlink(lb, index);
+       return rna_pointer_inherit_refine(ptr, type, data);
+}
+
 void rna_iterator_array_begin(CollectionPropertyIterator *iter, void *ptr, int itemsize, int length, int free_ptr, IteratorSkipFunc skip)
 {
        ArrayIterator *internal;
 
        if(ptr == NULL)
                length= 0;
+       else if (length == 0) {
+               ptr= NULL;
+               itemsize= 0;
+       }
 
        internal= MEM_callocN(sizeof(ArrayIterator), "ArrayIterator");
        internal->ptr= ptr;
@@ -2721,7 +3107,8 @@ void rna_iterator_array_begin(CollectionPropertyIterator *iter, void *ptr, int i
        internal->endptr= ((char*)ptr)+length*itemsize;
        internal->itemsize= itemsize;
        internal->skip= skip;
-
+       internal->length= length;
+       
        iter->internal= internal;
        iter->valid= (internal->ptr != internal->endptr);
 
@@ -2772,12 +3159,21 @@ void rna_iterator_array_end(CollectionPropertyIterator *iter)
        iter->internal= NULL;
 }
 
+PointerRNA rna_array_lookup_int(PointerRNA *ptr, StructRNA *type, void *data, int itemsize, int length, int index)
+{
+       if(index < 0 || index >= length)
+               return PointerRNA_NULL;
+
+       return rna_pointer_inherit_refine(ptr, type, ((char*)data) + index*itemsize);
+}
+
 /* RNA Path - Experiment */
 
 static char *rna_path_token(const char **path, char *fixedbuf, int fixedlen, int bracket)
 {
        const char *p;
        char *buf;
+       char quote= '\0';
        int i, j, len, escape;
 
        len= 0;
@@ -2789,9 +3185,30 @@ static char *rna_path_token(const char **path, char *fixedbuf, int fixedlen, int
 
                p= *path;
 
-               escape= 0;
-               while(*p && (*p != ']' || escape)) {
-                       escape= (*p == '\\');
+               /* 2 kinds of lookups now, quoted or unquoted */
+               quote= *p;
+
+               if(quote != '"') /* " - this comment is hack for Aligorith's text editor's sanity */
+                       quote= 0;
+
+               if(quote==0) {
+                       while(*p && (*p != ']')) {
+                               len++;
+                               p++;
+                       }
+               }
+               else {
+                       escape= 0;
+                       /* skip the first quote */
+                       len++;
+                       p++;
+                       while(*p && (*p != quote || escape)) {
+                               escape= (*p == '\\');
+                               len++;
+                               p++;
+                       }
+                       
+                       /* skip the last quoted char to get the ']' */
                        len++;
                        p++;
                }
@@ -2821,7 +3238,7 @@ static char *rna_path_token(const char **path, char *fixedbuf, int fixedlen, int
        /* copy string, taking into account escaped ] */
        if(bracket) {
                for(p=*path, i=0, j=0; i<len; i++, p++) {
-                       if(*p == '\\' && *(p+1) == ']');
+                       if(*p == '\\' && *(p+1) == quote);
                        else buf[j++]= *p;
                }
 
@@ -2864,7 +3281,7 @@ int RNA_path_resolve_full(PointerRNA *ptr, const char *path, PointerRNA *r_ptr,
        PropertyRNA *prop;
        PointerRNA curptr, nextptr;
        char fixedbuf[256], *token;
-       int type, len, intkey;
+       int type, intkey;
 
        prop= NULL;
        curptr= *ptr;
@@ -2885,7 +3302,7 @@ int RNA_path_resolve_full(PointerRNA *ptr, const char *path, PointerRNA *r_ptr,
                        return 0;
 
                if(use_id_prop) { /* look up property name in current struct */
-                       IDProperty *group= RNA_struct_idproperties(&curptr, 0);
+                       IDProperty *group= RNA_struct_idprops(&curptr, 0);
                        if(group && rna_token_strip_quotes(token))
                                prop= (PropertyRNA *)IDP_GetPropertyFromGroup(group, token+1);
                }
@@ -2908,41 +3325,61 @@ int RNA_path_resolve_full(PointerRNA *ptr, const char *path, PointerRNA *r_ptr,
                case PROP_POINTER:
                        nextptr= RNA_property_pointer_get(&curptr, prop);
 
-                       if(nextptr.data)
+                       if(nextptr.data) {
                                curptr= nextptr;
+                               prop= NULL; /* now we have a PointerRNA, the prop is our parent so forget it */
+                               if(index) *index= -1;
+                       }
                        else
                                return 0;
 
                        break;
                case PROP_COLLECTION:
                        if(*path) {
-                               /* resolve the lookup with [] brackets */
-                               token= rna_path_token(&path, fixedbuf, sizeof(fixedbuf), 1);
-
-                               if(!token)
-                                       return 0;
-
-                               len= strlen(token);
+                               if(*path == '[') {
+                                       /* resolve the lookup with [] brackets */
+                                       token= rna_path_token(&path, fixedbuf, sizeof(fixedbuf), 1);
+       
+                                       if(!token)
+                                               return 0;
+       
+                                       /* check for "" to see if it is a string */
+                                       if(rna_token_strip_quotes(token)) {
+                                               RNA_property_collection_lookup_string(&curptr, prop, token+1, &nextptr);
+                                       }
+                                       else {
+                                               /* otherwise do int lookup */
+                                               intkey= atoi(token);
+                                               if(intkey==0 && (token[0] != '0' || token[1] != '\0')) {
+                                                       return 0; /* we can be sure the fixedbuf was used in this case */
+                                               }
+                                               RNA_property_collection_lookup_int(&curptr, prop, intkey, &nextptr);
+                                       }
 
-                               /* check for "" to see if it is a string */
-                               if(rna_token_strip_quotes(token)) {
-                                       RNA_property_collection_lookup_string(&curptr, prop, token+1, &nextptr);
+                                       if(token != fixedbuf) {
+                                               MEM_freeN(token);
+                                       }
                                }
                                else {
-                                       /* otherwise do int lookup */
-                                       intkey= atoi(token);
-                                       RNA_property_collection_lookup_int(&curptr, prop, intkey, &nextptr);
-                               }
+                                       PointerRNA c_ptr;
+                                       
+                                       /* ensure we quit on invalid values */
+                                       nextptr.data = NULL;
 
-                               if(token != fixedbuf)
-                                       MEM_freeN(token);
+                                       if(RNA_property_collection_type_get(&curptr, prop, &c_ptr)) {
+                                               nextptr= c_ptr;
+                                       }
+                               }
 
-                               if(nextptr.data)
+                               if(nextptr.data) {
                                        curptr= nextptr;
+                                       prop= NULL;  /* now we have a PointerRNA, the prop is our parent so forget it */
+                                       if(index) *index= -1;
+                               }
                                else
                                        return 0;
                        }
-
+                       
                        break;
                default:
                        if (index==NULL)
@@ -2951,25 +3388,76 @@ int RNA_path_resolve_full(PointerRNA *ptr, const char *path, PointerRNA *r_ptr,
                        *index= -1;
 
                        if (*path) {
-                               if (*path=='[') {
-                                       token= rna_path_token(&path, fixedbuf, sizeof(fixedbuf), 1);
+                               int index_arr[RNA_MAX_ARRAY_DIMENSION]= {0};
+                               int len[RNA_MAX_ARRAY_DIMENSION];
+                               const int dim= RNA_property_array_dimension(&curptr, prop, len);
+                               int i, temp_index;
 
-                                       /* check for "" to see if it is a string */
-                                       if(rna_token_strip_quotes(token)) {
-                                               *index= RNA_property_array_item_index(prop, *(token+1));
+                               for(i=0; i<dim; i++) {
+                                       temp_index= -1; 
+
+                                       /* multi index resolve */
+                                       if (*path=='[') {
+                                               token= rna_path_token(&path, fixedbuf, sizeof(fixedbuf), 1);
+       
+                                               if(token==NULL) {
+                                                       /* invalid syntax blah[] */
+                                                       return 0;
+                                               }
+                                               /* check for "" to see if it is a string */
+                                               else if(rna_token_strip_quotes(token)) {
+                                                       temp_index= RNA_property_array_item_index(prop, *(token+1));
+                                               }
+                                               else {
+                                                       /* otherwise do int lookup */
+                                                       temp_index= atoi(token);
+
+                                                       if(temp_index==0 && (token[0] != '0' || token[1] != '\0')) {
+                                                               if(token != fixedbuf) {
+                                                                       MEM_freeN(token);
+                                                               }
+
+                                                               return 0;
+                                                       }
+                                               }
                                        }
-                                       else {
-                                               /* otherwise do int lookup */
-                                               *index= atoi(token);
+                                       else if(dim==1) {
+                                               /* location.x || scale.X, single dimension arrays only */
+                                               token= rna_path_token(&path, fixedbuf, sizeof(fixedbuf), 0);
+                                               if(token==NULL) {
+                                                       /* invalid syntax blah.. */
+                                                       return 0;
+                                               }
+                                               temp_index= RNA_property_array_item_index(prop, *token);
                                        }
+       
+                                       if(token != fixedbuf) {
+                                               MEM_freeN(token);
+                                       }
+                                       
+                                       /* out of range */
+                                       if(temp_index < 0 || temp_index >= len[i])
+                                               return 0;
+
+                                       index_arr[i]= temp_index;
+                                       /* end multi index resolve */
                                }
-                               else {
-                                       token= rna_path_token(&path, fixedbuf, sizeof(fixedbuf), 0);
-                                       *index= RNA_property_array_item_index(prop, *token);
+
+                               /* arrays always contain numbers so further values are not valid */
+                               if(*path) {
+                                       return 0;
                                }
+                               else {
+                                       int totdim= 1;
+                                       int flat_index= 0;
+
+                                       for(i=dim-1; i>=0; i--) {
+                                               flat_index += index_arr[i] * totdim;
+                                               totdim *= len[i];
+                                       }
 
-                               if(token != fixedbuf)
-                                       MEM_freeN(token);
+                                       *index= flat_index;
+                               }
                        }
                }
        }
@@ -2981,7 +3469,7 @@ int RNA_path_resolve_full(PointerRNA *ptr, const char *path, PointerRNA *r_ptr,
 }
 
 
-char *RNA_path_append(const char *path, PointerRNA *ptr, PropertyRNA *prop, int intkey, const char *strkey)
+char *RNA_path_append(const char *path, PointerRNA *UNUSED(ptr), PropertyRNA *prop, int intkey, const char *strkey)
 {
        DynStr *dynstr;
        const char *s;
@@ -3019,7 +3507,7 @@ char *RNA_path_append(const char *path, PointerRNA *ptr, PropertyRNA *prop, int
                        BLI_dynstr_append(dynstr, "\"");
                }
                else {
-                       sprintf(appendstr, "%d", intkey);
+                       BLI_snprintf(appendstr, sizeof(appendstr), "%d", intkey);
                        BLI_dynstr_append(dynstr, appendstr);
                }
 
@@ -3079,6 +3567,143 @@ char *RNA_path_back(const char *path)
        return result;
 }
 
+/* generic path search func
+ * if its needed this could also reference the IDProperty direct */
+typedef struct IDP_Chain {
+       struct IDP_Chain *up; /* parent member, reverse and set to child for path conversion. */
+
+       const char *name;
+       int index;
+
+} IDP_Chain;
+
+static char *rna_idp_path_create(IDP_Chain *child_link)
+{
+       DynStr *dynstr= BLI_dynstr_new();
+       char *path;
+       short first= TRUE;
+
+       int tot= 0;
+       IDP_Chain *link= child_link;
+
+       /* reverse the list */
+       IDP_Chain *link_prev;
+       link_prev= NULL;
+       while(link) {
+               IDP_Chain *link_next= link->up;
+               link->up= link_prev;
+               link_prev= link;
+               link= link_next;
+               tot++;
+       }
+
+       for(link= link_prev; link; link= link->up) {
+               /* pass */
+               if(link->index >= 0) {
+                       BLI_dynstr_appendf(dynstr, first ? "%s[%d]" : ".%s[%d]", link->name, link->index);
+               }
+               else {
+                       BLI_dynstr_appendf(dynstr, first ? "%s" : ".%s", link->name);
+               }
+
+               first= FALSE;
+       }
+
+       path= BLI_dynstr_get_cstring(dynstr);
+       BLI_dynstr_free(dynstr);
+
+       if(*path=='\0') {
+               MEM_freeN(path);
+               path= NULL;
+       }
+
+       return path;
+}
+
+static char *rna_idp_path(PointerRNA *ptr, IDProperty *haystack, IDProperty *needle, IDP_Chain *parent_link)
+{
+       char *path= NULL;
+       IDP_Chain link;
+
+       IDProperty *iter;
+       int i;
+
+       BLI_assert(haystack->type == IDP_GROUP);
+
+       link.up= parent_link;
+       link.name= NULL;
+       link.index= -1;
+
+       for (i=0, iter= haystack->data.group.first; iter; iter= iter->next, i++) {
+               if(needle == iter) {  /* found! */
+                       link.name= iter->name;
+                       path= rna_idp_path_create(&link);
+                       break;
+               }
+               else {
+                       if(iter->type == IDP_GROUP) {
+                               /* ensure this is RNA */
+                               PointerRNA child_ptr= RNA_pointer_get(ptr, iter->name);
+                               if(child_ptr.type) {
+                                       link.name= iter->name;
+                                       if((path= rna_idp_path(&child_ptr, iter, needle, &link))) {
+                                               break;
+                                       }
+                               }
+                       }
+                       else if (iter->type == IDP_IDPARRAY) {
+                               PropertyRNA *prop= RNA_struct_find_property(ptr, iter->name);
+                               if(prop && prop->type == PROP_COLLECTION) {
+                                       IDProperty *array= IDP_IDPArray(iter);
+                                       if(needle >= array && needle < (iter->len + array)) { /* found! */
+                                               link.name= iter->name;
+                                               link.index= (int)(needle - array);
+                                               path= rna_idp_path_create(&link);
+                                               break;
+                                       }
+                                       else {
+                                               int i;
+                                               link.name= iter->name;
+                                               for(i= 0; i < iter->len; i++, array++) {
+                                                       PointerRNA child_ptr;
+                                                       if(RNA_property_collection_lookup_int(ptr, prop, i, &child_ptr)) {
+                                                               link.index= i;
+                                                               if((path= rna_idp_path(&child_ptr, array, needle, &link))) {
+                                                                       break;
+                                                               }
+                                                       }
+                                               }
+                                       }
+                               }
+                       }
+               }
+       }
+
+       return path;
+}
+
+static char *rna_path_from_ID_to_idpgroup(PointerRNA *ptr)
+{
+       PointerRNA id_ptr;
+       IDProperty *haystack;
+       IDProperty *needle;
+
+       BLI_assert(ptr->id.data != NULL);
+
+       /* TODO, Support Bones/PoseBones. no pointers stored to the bones from here, only the ID. See example in [#25746]
+        * unless this is added only way to find this is to also search all bones and pose bones of an armature or object */
+       RNA_id_pointer_create(ptr->id.data, &id_ptr);
+
+       haystack= RNA_struct_idprops(&id_ptr, FALSE);
+       if(haystack) { /* can fail when called on bones */
+               needle= ptr->data;
+               return rna_idp_path(&id_ptr, haystack, needle, NULL);
+       }
+       else {
+               return NULL;
+       }
+}
+
 char *RNA_path_from_ID_to_struct(PointerRNA *ptr)
 {
        char *ptrpath=NULL;
@@ -3106,6 +3731,10 @@ char *RNA_path_from_ID_to_struct(PointerRNA *ptr)
                        else
                                return NULL; // can't do anything about this case yet...
                }
+               else if (RNA_struct_is_a(ptr->type, &RNA_PropertyGroup)) {
+                       /* special case, easier to deal with here then in ptr->type->path() */
+                       return rna_path_from_ID_to_idpgroup(ptr);
+               }
                else
                        return NULL;
        }
@@ -3358,6 +3987,18 @@ int      RNA_enum_id_from_value(EnumPropertyItem *item, int value, const char **ident
        return 0;
 }
 
+int RNA_enum_icon_from_value(EnumPropertyItem *item, int value, int *icon)
+{
+       for( ; item->identifier; item++) {
+               if(item->value==value) {
+                       *icon = item->icon;
+                       return 1;
+               }
+       }
+       
+       return 0;
+}
+
 void RNA_string_get(PointerRNA *ptr, const char *name, char *value)
 {
        PropertyRNA *prop= RNA_struct_find_property(ptr, name);
@@ -3377,7 +4018,7 @@ char *RNA_string_get_alloc(PointerRNA *ptr, const char *name, char *fixedbuf, in
        }
        else {
                printf("RNA_string_get_alloc: %s.%s not found.\n", ptr->type->identifier, name);
-               return 0;
+               return NULL;
        }
 }
 
@@ -3412,12 +4053,9 @@ PointerRNA RNA_pointer_get(PointerRNA *ptr, const char *name)
                return RNA_property_pointer_get(ptr, prop);
        }
        else {
-               PointerRNA result;
-
                printf("RNA_pointer_get: %s.%s not found.\n", ptr->type->identifier, name);
 
-               memset(&result, 0, sizeof(result));
-               return result;
+               return PointerRNA_NULL;
        }
 }
 
@@ -3497,7 +4135,8 @@ int RNA_property_is_set(PointerRNA *ptr, const char *name)
                        return 1;
        }
        else {
-               // printf("RNA_property_is_set: %s.%s not found.\n", ptr->type->identifier, name);
+               /* python raises an error */
+               /* printf("RNA_property_is_set: %s.%s not found.\n", ptr->type->identifier, name); */
                return 0;
        }
 }
@@ -3508,8 +4147,9 @@ int RNA_property_is_idprop(PropertyRNA *prop)
 }
 
 /* string representation of a property, python
- * compatible but can be used for display too*/
-char *RNA_pointer_as_string(PointerRNA *ptr)
+ * compatible but can be used for display too,
+ * context may be NULL */
+char *RNA_pointer_as_string(bContext *C, PointerRNA *ptr)
 {
        DynStr *dynstr= BLI_dynstr_new();
        char *cstring;
@@ -3529,7 +4169,7 @@ char *RNA_pointer_as_string(PointerRNA *ptr)
                        BLI_dynstr_append(dynstr, ", ");
                first_time= 0;
                
-               cstring = RNA_property_as_string(NULL, ptr, prop);
+               cstring = RNA_property_as_string(C, ptr, prop);
                BLI_dynstr_appendf(dynstr, "\"%s\":%s", propname, cstring);
                MEM_freeN(cstring);
        }
@@ -3612,17 +4252,44 @@ char *RNA_property_as_string(bContext *C, PointerRNA *ptr, PropertyRNA *prop)
                const char *identifier;
                int val = RNA_property_enum_get(ptr, prop);
 
-               if(RNA_property_enum_identifier(C, ptr, prop, val, &identifier)) {
+               if(RNA_property_flag(prop) & PROP_ENUM_FLAG) {
+                       /* represent as a python set */
+                       EnumPropertyItem *item= NULL;
+                       int free;
+
+                       BLI_dynstr_append(dynstr, "{");
+
+                       RNA_property_enum_items(C, ptr, prop, &item, NULL, &free);
+                       if(item) {
+                               short is_first= TRUE;
+                               for (; item->identifier; item++) {
+                                       if(item->identifier[0] && item->value & val) {
+                                               BLI_dynstr_appendf(dynstr, is_first ? "'%s'" : ", '%s'", item->identifier);
+                                               is_first= FALSE;
+                                       }
+                               }
+
+                               if(free) {
+                                       MEM_freeN(item);
+                               }
+                       }
+
+                       BLI_dynstr_append(dynstr, "}");
+               }
+               else if(RNA_property_enum_identifier(C, ptr, prop, val, &identifier)) {
                        BLI_dynstr_appendf(dynstr, "'%s'", identifier);
                }
                else {
-                       BLI_dynstr_appendf(dynstr, "'<UNKNOWN ENUM>'", identifier);
+                       BLI_dynstr_append(dynstr, "'<UNKNOWN ENUM>'");
                }
                break;
        }
        case PROP_POINTER:
        {
-               BLI_dynstr_append(dynstr, "'<POINTER>'"); /* TODO */
+               PointerRNA tptr= RNA_property_pointer_get(ptr, prop);
+               cstring= RNA_pointer_as_string(C, &tptr);
+               BLI_dynstr_append(dynstr, cstring);
+               MEM_freeN(cstring);
                break;
        }
        case PROP_COLLECTION:
@@ -3639,7 +4306,7 @@ char *RNA_property_as_string(bContext *C, PointerRNA *ptr, PropertyRNA *prop)
                        first_time= 0;
                        
                        /* now get every prop of the collection */
-                       cstring= RNA_pointer_as_string(&itemptr);
+                       cstring= RNA_pointer_as_string(C, &itemptr);
                        BLI_dynstr_append(dynstr, cstring);
                        MEM_freeN(cstring);
                }
@@ -3680,29 +4347,14 @@ int RNA_function_defined(FunctionRNA *func)
        return func->call != NULL;
 }
 
-PropertyRNA *RNA_function_get_parameter(PointerRNA *ptr, FunctionRNA *func, int index)
+PropertyRNA *RNA_function_get_parameter(PointerRNA *UNUSED(ptr), FunctionRNA *func, int index)
 {
-       PropertyRNA *parm;
-       int i;
-
-       parm= func->cont.properties.first;
-       for(i= 0; parm; parm= parm->next, i++)
-               if(i==index)
-                       return parm;
-
-       return NULL;
+       return BLI_findlink(&func->cont.properties, index);
 }
 
-PropertyRNA *RNA_function_find_parameter(PointerRNA *ptr, FunctionRNA *func, const char *identifier)
+PropertyRNA *RNA_function_find_parameter(PointerRNA *UNUSED(ptr), FunctionRNA *func, const char *identifier)
 {
-       PropertyRNA *parm;
-
-       parm= func->cont.properties.first;
-       for(; parm; parm= parm->next)
-               if(strcmp(parm->identifier, identifier)==0)
-                       return parm;
-
-       return NULL;
+       return BLI_findstring(&func->cont.properties, identifier, offsetof(PropertyRNA, identifier));
 }
 
 const struct ListBase *RNA_function_defined_parameters(FunctionRNA *func)
@@ -3712,19 +4364,28 @@ const struct ListBase *RNA_function_defined_parameters(FunctionRNA *func)
 
 /* Utility */
 
-ParameterList *RNA_parameter_list_create(ParameterList *parms, PointerRNA *ptr, FunctionRNA *func)
+ParameterList *RNA_parameter_list_create(ParameterList *parms, PointerRNA *UNUSED(ptr), FunctionRNA *func)
 {
        PropertyRNA *parm;
        void *data;
-       int tot= 0, size;
+       int alloc_size= 0, size;
+
+       parms->arg_count= 0;
+       parms->ret_count= 0;
 
        /* allocate data */
-       for(parm= func->cont.properties.first; parm; parm= parm->next)
-               tot+= rna_parameter_size_alloc(parm);
+       for(parm= func->cont.properties.first; parm; parm= parm->next) {
+               alloc_size += rna_parameter_size_alloc(parm);
+
+               if(parm->flag & PROP_OUTPUT)
+                       parms->ret_count++;
+               else
+                       parms->arg_count++;
+       }
 
-       parms->data= MEM_callocN(tot, "RNA_parameter_list_create");
+       parms->data= MEM_callocN(alloc_size, "RNA_parameter_list_create");
        parms->func= func;
-       parms->tot= tot;
+       parms->alloc_size= alloc_size;
 
        /* set default values */
        data= parms->data;
@@ -3732,7 +4393,14 @@ ParameterList *RNA_parameter_list_create(ParameterList *parms, PointerRNA *ptr,
        for(parm= func->cont.properties.first; parm; parm= parm->next) {
                size= rna_parameter_size(parm);
 
-               if(!(parm->flag & PROP_REQUIRED)) {
+               /* set length to 0, these need to be set later, see bpy_array.c's py_to_array */
+               if (parm->flag & PROP_DYNAMIC) {
+                       ParameterDynAlloc *data_alloc= data;
+                       data_alloc->array_tot= 0;
+                       data_alloc->array= NULL;
+               }
+               
+               if(!(parm->flag & PROP_REQUIRED) && !(parm->flag & PROP_DYNAMIC)) {
                        switch(parm->type) {
                                case PROP_BOOLEAN:
                                        if(parm->arraydimension) memcpy(data, &((BooleanPropertyRNA*)parm)->defaultarray, size);
@@ -3761,10 +4429,6 @@ ParameterList *RNA_parameter_list_create(ParameterList *parms, PointerRNA *ptr,
                        }
                }
 
-               /* set length to 0 */
-               if (parm->flag & PROP_DYNAMIC)
-                       *((int *)(((char *)data) + size))= 0;
-
                data= ((char*)data) + rna_parameter_size_alloc(parm);
        }
 
@@ -3782,9 +4446,9 @@ void RNA_parameter_list_free(ParameterList *parms)
                        BLI_freelistN((ListBase*)((char*)parms->data+tot));
                else if (parm->flag & PROP_DYNAMIC) {
                        /* for dynamic arrays and strings, data is a pointer to an array */
-                       char *array= *(char**)((char*)parms->data+tot);
-                       if(array)
-                               MEM_freeN(array);
+                       ParameterDynAlloc *data_alloc= (void *)(((char *)parms->data) + tot);
+                       if(data_alloc->array)
+                               MEM_freeN(data_alloc->array);
                }
 
                tot+= rna_parameter_size_alloc(parm);
@@ -3798,13 +4462,21 @@ void RNA_parameter_list_free(ParameterList *parms)
 
 int  RNA_parameter_list_size(ParameterList *parms)
 {
-       return parms->tot;
+       return parms->alloc_size;
 }
 
-void RNA_parameter_list_begin(ParameterList *parms, ParameterIterator *iter)
+int  RNA_parameter_list_arg_count(ParameterList *parms)
 {
-       PropertyType ptype;
+       return parms->arg_count;
+}
 
+int  RNA_parameter_list_ret_count(ParameterList *parms)
+{
+       return parms->ret_count;
+}
+
+void RNA_parameter_list_begin(ParameterList *parms, ParameterIterator *iter)
+{
        RNA_pointer_create(NULL, &RNA_Function, parms->func, &iter->funcptr);
 
        iter->parms= parms;
@@ -3814,15 +4486,12 @@ void RNA_parameter_list_begin(ParameterList *parms, ParameterIterator *iter)
 
        if(iter->valid) {
                iter->size= rna_parameter_size_alloc(iter->parm);
-               iter->data= (((char*)iter->parms->data)+iter->offset);
-               ptype= RNA_property_type(iter->parm);
+               iter->data= (((char*)iter->parms->data)); /* +iter->offset, always 0 */
        }
 }
 
 void RNA_parameter_list_next(ParameterIterator *iter)
 {
-       PropertyType ptype;
-
        iter->offset+= iter->size;
        iter->parm= iter->parm->next;
        iter->valid= iter->parm != NULL;
@@ -3830,11 +4499,10 @@ void RNA_parameter_list_next(ParameterIterator *iter)
        if(iter->valid) {
                iter->size= rna_parameter_size_alloc(iter->parm);
                iter->data= (((char*)iter->parms->data)+iter->offset);
-               ptype= RNA_property_type(iter->parm);
        }
 }
 
-void RNA_parameter_list_end(ParameterIterator *iter)
+void RNA_parameter_list_end(ParameterIterator *UNUSED(iter))
 {
        /* nothing to do */
 }
@@ -3870,7 +4538,7 @@ void RNA_parameter_get_lookup(ParameterList *parms, const char *identifier, void
                RNA_parameter_get(parms, parm, value);
 }
 
-void RNA_parameter_set(ParameterList *parms, PropertyRNA *parm, void *value)
+void RNA_parameter_set(ParameterList *parms, PropertyRNA *parm, const void *value)
 {
        ParameterIterator iter;
 
@@ -3886,7 +4554,7 @@ void RNA_parameter_set(ParameterList *parms, PropertyRNA *parm, void *value)
        RNA_parameter_list_end(&iter);
 }
 
-void RNA_parameter_set_lookup(ParameterList *parms, const char *identifier, void *value)
+void RNA_parameter_set_lookup(ParameterList *parms, const char *identifier, const void *value)
 {
        PropertyRNA *parm;
 
@@ -3934,14 +4602,14 @@ void RNA_parameter_length_set(ParameterList *parms, PropertyRNA *parm, int lengt
        RNA_parameter_list_end(&iter);
 }
 
-int RNA_parameter_length_get_data(ParameterList *parms, PropertyRNA *parm, void *data)
+int RNA_parameter_length_get_data(ParameterList *UNUSED(parms), PropertyRNA *UNUSED(parm), void *data)
 {
-       return *((int *)(((char *)data) + rna_parameter_size(parm)));
+       return *((int *)((char *)data));
 }
 
-void RNA_parameter_length_set_data(ParameterList *parms, PropertyRNA *parm, void *data, int length)
+void RNA_parameter_length_set_data(ParameterList *UNUSED(parms), PropertyRNA *UNUSED(parm), void *data, int length)
 {
-       *((int *)(((char *)data) + rna_parameter_size(parm)))= length;
+       *((int *)data)= length;
 }
 
 int RNA_function_call(bContext *C, ReportList *reports, PointerRNA *ptr, FunctionRNA *func, ParameterList *parms)
@@ -4012,7 +4680,7 @@ static int rna_function_format_array_length(const char *format, int ofs, int fle
                for (; ofs<flen && format[ofs]!=']' && idx<sizeof(*lenbuf)-1; idx++, ofs++)
                        lenbuf[idx]= format[ofs];
 
-       if (ofs<flen && format[ofs++]==']') {
+       if (ofs<flen && format[ofs+1]==']') {
                /* XXX put better error reporting for ofs>=flen or idx over lenbuf capacity */
                lenbuf[idx]= '\0';
                return atoi(lenbuf);
@@ -4104,7 +4772,7 @@ static int rna_function_parameter_parse(PointerRNA *ptr, PropertyRNA *prop, Prop
                        if(prop->flag & PROP_RNAPTR) {
                                *((PointerRNA*)dest)= *((PointerRNA*)src);
                                break;
-                       }
+                        }
                        
                        if (ptype!=srna && !RNA_struct_is_a(srna, ptype)) {
                                fprintf(stderr, "%s.%s: wrong type for parameter %s, an object of type %s was expected, passed an object of type %s\n", tid, fid, pid, RNA_struct_identifier(ptype), RNA_struct_identifier(srna));
@@ -4426,9 +5094,15 @@ int RNA_property_reset(PointerRNA *ptr, PropertyRNA *prop, int index)
                        return 1;
                }
                
-               //case PROP_POINTER:
+               case PROP_POINTER:
+               {
+                       PointerRNA value= RNA_property_pointer_get_default(ptr, prop);
+                       RNA_property_pointer_set(ptr, prop, value);
+                       return 1;
+               }
+               
                default: 
-                       // FIXME: many of the other types such as strings and pointers need this implemented too!
+                       // FIXME: are there still any cases that haven't been handled? comment out "default" block to check :)
                        return 0;
        }
 }
@@ -4532,3 +5206,18 @@ int RNA_property_copy(PointerRNA *ptr, PointerRNA *fromptr, PropertyRNA *prop, i
        return 0;
 }
 
+void RNA_warning(const char *format, ...)
+{
+       va_list args;
+
+       va_start(args, format);
+       vprintf(format, args);
+       va_end(args);
+
+#ifdef WITH_PYTHON
+       {
+               extern void PyC_LineSpit(void);
+               PyC_LineSpit();
+       }
+#endif
+}