CodeArrayItem.cs 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178
  1. //
  2. // Permission is hereby granted, free of charge, to any person obtaining
  3. // a copy of this software and associated documentation files (the
  4. // "Software"), to deal in the Software without restriction, including
  5. // without limitation the rights to use, copy, modify, merge, publish,
  6. // distribute, sublicense, and/or sell copies of the Software, and to
  7. // permit persons to whom the Software is furnished to do so, subject to
  8. // the following conditions:
  9. //
  10. // The above copyright notice and this permission notice shall be
  11. // included in all copies or substantial portions of the Software.
  12. //
  13. // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
  14. // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
  15. // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
  16. // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
  17. // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
  18. // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
  19. // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  20. //
  21. // Copyright (C) Lluis Sanchez Gual, 2004
  22. //
  23. #if !FULL_AOT_RUNTIME
  24. using System;
  25. using System.Reflection;
  26. using System.Reflection.Emit;
  27. namespace Mono.CodeGeneration
  28. {
  29. public class CodeArrayItem: CodeValueReference
  30. {
  31. CodeExpression array;
  32. CodeExpression index;
  33. public CodeArrayItem (CodeExpression array, CodeExpression index)
  34. {
  35. if (array == null)
  36. throw new ArgumentNullException ("array");
  37. if (index == null)
  38. throw new ArgumentNullException ("index");
  39. this.array = array;
  40. this.index = index;
  41. }
  42. public override void Generate (ILGenerator gen)
  43. {
  44. array.Generate (gen);
  45. index.Generate (gen);
  46. Type t = array.GetResultType().GetElementType();
  47. if (t.IsEnum && t != typeof(Enum)) t = t.UnderlyingSystemType;
  48. switch (Type.GetTypeCode (t))
  49. {
  50. case TypeCode.Byte:
  51. gen.Emit (OpCodes.Ldelem_U1);
  52. break;
  53. case TypeCode.Double:
  54. gen.Emit (OpCodes.Ldelem_R8);
  55. break;
  56. case TypeCode.Int16:
  57. gen.Emit (OpCodes.Ldelem_I2);
  58. break;
  59. case TypeCode.UInt32:
  60. gen.Emit (OpCodes.Ldelem_U4);
  61. break;
  62. case TypeCode.Int32:
  63. gen.Emit (OpCodes.Ldelem_I4);
  64. break;
  65. case TypeCode.UInt64:
  66. case TypeCode.Int64:
  67. gen.Emit (OpCodes.Ldelem_I8);
  68. break;
  69. case TypeCode.SByte:
  70. gen.Emit (OpCodes.Ldelem_I1);
  71. break;
  72. case TypeCode.Single:
  73. gen.Emit (OpCodes.Ldelem_R4);
  74. break;
  75. case TypeCode.UInt16:
  76. gen.Emit (OpCodes.Ldelem_U2);
  77. break;
  78. default:
  79. if (t.IsValueType) {
  80. gen.Emit (OpCodes.Ldelema, t);
  81. CodeGenerationHelper.LoadFromPtr (gen, t);
  82. }
  83. else
  84. gen.Emit (OpCodes.Ldelem_Ref);
  85. break;
  86. }
  87. }
  88. public override void GenerateSet (ILGenerator gen, CodeExpression value)
  89. {
  90. if (value == null)
  91. throw new ArgumentNullException ("value");
  92. Type t = array.GetResultType().GetElementType();
  93. if (t.IsEnum && t != typeof(Enum)) t = t.UnderlyingSystemType;
  94. array.Generate (gen);
  95. index.Generate (gen);
  96. switch (Type.GetTypeCode (t))
  97. {
  98. case TypeCode.Byte:
  99. case TypeCode.SByte:
  100. value.Generate (gen);
  101. gen.Emit (OpCodes.Stelem_I1);
  102. break;
  103. case TypeCode.Double:
  104. value.Generate (gen);
  105. gen.Emit (OpCodes.Stelem_R8);
  106. break;
  107. case TypeCode.UInt16:
  108. case TypeCode.Int16:
  109. value.Generate (gen);
  110. gen.Emit (OpCodes.Stelem_I2);
  111. break;
  112. case TypeCode.UInt32:
  113. case TypeCode.Int32:
  114. value.Generate (gen);
  115. gen.Emit (OpCodes.Stelem_I4);
  116. break;
  117. case TypeCode.UInt64:
  118. case TypeCode.Int64:
  119. value.Generate (gen);
  120. gen.Emit (OpCodes.Stelem_I8);
  121. break;
  122. case TypeCode.Single:
  123. value.Generate (gen);
  124. gen.Emit (OpCodes.Stelem_R4);
  125. break;
  126. default:
  127. if (t.IsValueType) {
  128. gen.Emit (OpCodes.Ldelema, t);
  129. value.Generate (gen);
  130. gen.Emit (OpCodes.Stobj, t);
  131. }
  132. else {
  133. value.Generate (gen);
  134. gen.Emit (OpCodes.Stelem_Ref);
  135. }
  136. break;
  137. }
  138. }
  139. public override void PrintCode (CodeWriter cp)
  140. {
  141. array.PrintCode (cp);
  142. cp.Write ("[");
  143. index.PrintCode (cp);
  144. cp.Write ("]");
  145. }
  146. public override Type GetResultType ()
  147. {
  148. return array.GetResultType().GetElementType();
  149. }
  150. }
  151. }
  152. #endif