/// <summary> /// Constructs a new command line argument. /// </summary> /// <param name="attribute">The attribute that defines the argument</param> /// <param name="propertyInfo">The arguments property information</param> public CommandLineArgument(CommandLineArgumentAttribute attribute, PropertyInfo propertyInfo) { // Set these two things first this.attribute = attribute; this.propertyInfo = propertyInfo; if (this.IsArray) { // Get an element type if the argument is an array valueType = propertyInfo.PropertyType.GetElementType(); if (valueType == typeof(object)) { throw new NotSupportedException(CommandLineParserResources.PropertyIsNotAStronglyTypedArray(propertyInfo.Name)); } } else if (this.IsCollection) { // Locate Add method with 1 parameter that is not System.Object foreach (MethodInfo method in propertyInfo.PropertyType.GetMethods(BindingFlags.Public | BindingFlags.Instance)) { if (method.Name == "Add" && method.GetParameters().Length == 1) { ParameterInfo parameter = method.GetParameters()[0]; if (parameter.ParameterType != typeof(object)) { addMethod = method; valueType = parameter.ParameterType; } } if (method.Name == "GetEnumerator" && method.GetParameters().Length == 0 && typeof(IEnumerator).IsAssignableFrom(method.ReturnType)) { getEnumeratorMethod = method; } if (addMethod != null && getEnumeratorMethod != null) break; } // If we didn't find an appropriate Add method we can't write to the collection if (addMethod == null) { throw new NotSupportedException(CommandLineParserResources.PropertyHasNoAddMethodWithNonObjectParameter(propertyInfo.Name)); } // The collection derives from ICollection, so it would be really surprising if it didn't implement GetEnumerator Debug.Assert(getEnumeratorMethod != null); } else { // The argument is not an array or collection, so it's safe to take the property type as the value type this.valueType = propertyInfo.PropertyType; } this.values = new ArrayList(AllowMultiple ? 4 : 1); }
/// <summary> /// Constructs a new command line argument. /// </summary> /// <param name="attribute">The attribute that defines the argument</param> /// <param name="propertyInfo">The arguments property information</param> internal CommandLineArgument(object argTarget, CommandLineArgumentAttribute argAttribute, PropertyInfo argPropertyInfo) { // Set these two things first this.argTarget = argTarget; this.argType = argPropertyInfo.PropertyType; this.argPropertyInfo = argPropertyInfo; this.argAttribute = argAttribute; if (typeof(ICollection).IsAssignableFrom(argType)) { if (argType.IsArray) throw new NotSupportedException(CommandLineParserResources.ArraysAreNotSupported(argPropertyInfo.Name)); // Locate Add method with 1 parameter that is not System.Object foreach (MethodInfo method in argPropertyInfo.PropertyType.GetMethods(BindingFlags.Public | BindingFlags.Instance)) { if (method.Name == "Add" && method.GetParameters().Length == 1) { ParameterInfo parameter = method.GetParameters()[0]; if (parameter.ParameterType != typeof(object)) { argAddMethod = method; argType = parameter.ParameterType; break; } } } // If we didn't find an appropriate Add method we can't write to the collection if (argAddMethod == null) { throw new NotSupportedException(CommandLineParserResources.PropertyHasNoAddMethodWithNonObjectParameter(argPropertyInfo.Name)); } } }