CustomAttributeCreator.cpp 2.3 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071
  1. #include "CustomAttributeCreator.h"
  2. #include "gc/WriteBarrier.h"
  3. #include "vm/Class.h"
  4. #include "vm/Exception.h"
  5. #include "vm/Field.h"
  6. #include "vm/Method.h"
  7. #include "vm/Object.h"
  8. #include "vm/Property.h"
  9. #include "vm/Runtime.h"
  10. namespace il2cpp
  11. {
  12. namespace metadata
  13. {
  14. static void* ConvertArgumentValue(const Il2CppType* targetType, const CustomAttributeArgument* arg)
  15. {
  16. // If the argument target target is a value type, then just pass a pointer to the data
  17. if (targetType->valuetype)
  18. return (void*)&arg->data;
  19. // Our target isn't value type, but our data is, we need to box
  20. if (il2cpp::vm::Class::IsValuetype(arg->klass))
  21. return il2cpp::vm::Object::Box(arg->klass, (void*)&arg->data);
  22. // Storing reference type data in a reference type field, just get the pointer to the object
  23. return arg->data.obj;
  24. }
  25. void CustomAttributeCreator::VisitCtor(const MethodInfo* ctor, CustomAttributeArgument args[], uint32_t argumentCount)
  26. {
  27. attr = il2cpp::vm::Object::New(ctor->klass);
  28. void** ctorArgs = (void**)alloca(argumentCount * sizeof(void*));
  29. for (uint32_t i = 0; i < argumentCount; i++)
  30. ctorArgs[i] = ConvertArgumentValue(ctor->parameters[i], args + i);
  31. il2cpp::vm::Runtime::Invoke(ctor, attr, ctorArgs, &exc);
  32. if (exc != NULL)
  33. attr = NULL;
  34. }
  35. void CustomAttributeCreator::VisitField(const CustomAttributeFieldArgument& field, uint32_t index)
  36. {
  37. if (exc != NULL)
  38. return;
  39. IL2CPP_ASSERT(attr);
  40. il2cpp::vm::Field::SetValue(attr, field.field, ConvertArgumentValue(field.field->type, &field.arg));
  41. }
  42. void CustomAttributeCreator::VisitProperty(const CustomAttributePropertyArgument& prop, uint32_t index)
  43. {
  44. if (exc != NULL)
  45. return;
  46. IL2CPP_ASSERT(attr);
  47. const MethodInfo* setMethod = il2cpp::vm::Property::GetSetMethod(prop.prop);
  48. IL2CPP_ASSERT(setMethod->parameters_count == 1);
  49. void* param = ConvertArgumentValue(setMethod->parameters[0], &prop.arg);
  50. il2cpp::vm::Runtime::Invoke(setMethod, attr, &param, &exc);
  51. }
  52. Il2CppObject* CustomAttributeCreator::GetAttribute(Il2CppException** exc)
  53. {
  54. *exc = this->exc;
  55. return attr;
  56. }
  57. } /* namespace vm */
  58. } /* namespace il2cpp */