void EmitColumnCode(ColumnDefinition cd)
        {
            //  Ldarg_0 : DbfTableDefinitions
            //  Ldarg_1 : Byte[]
            //  Ldarg_2 : DbfRecord
            if (cd.mColumnType == ColumnType.DELAYED)
            {
                return;
            }

            string readMethodName;
            string writeMethodName;

            string dbfType = cd.mColumnType.ToString();
            string nativeType;

            Type fieldType = cd.mFieldInfo.FieldType;

            nativeType = fieldType.Name;

            if (fieldType.IsGenericType)
            {
                if (fieldType.GetGenericTypeDefinition() == typeof(Nullable <>))
                {
                    nativeType = "Nullable" + fieldType.GetGenericArguments()[0].Name;
                }
            }
            else if (fieldType.IsArray)
            {
                nativeType = fieldType.GetElementType().Name + "Array";
            }
            else if (fieldType.IsEnum)
            {
                nativeType = Type.GetTypeCode(fieldType).ToString();
            }


            readMethodName = "Read_" + dbfType
                             + "_" + nativeType;
            writeMethodName = "Write_" + nativeType
                              + "_" + dbfType;



            var writeXXX = this.GetType().GetMethod(
                writeMethodName,
                BindingFlags.NonPublic | BindingFlags.Static);

            if (writeXXX == null)
            {
                throw new Exception(string.Format("Unknown Method : {0}.", writeMethodName));
            }
            //void WriteXXX(
            mIlWrite.Emit(OpCodes.Ldarg_1);                 // << 1:Byte[] bytes
            mIlWrite.Emit(OpCodes.Ldarg_0);                 // << 2:dbfTable
            mIlWrite.Emit(OpCodes.Ldc_I4, cd.ColumnIndex);  // << 3: ColumIndex
            mIlWrite.Emit(OpCodes.Ldc_I4, cd.mOffset);      // << 4:Offset // for speed
            mIlWrite.Emit(OpCodes.Ldc_I4, cd.mWidth);       // << 5:Length // for speed
            mIlWrite.Emit(OpCodes.Ldarg_2);                 // <  Record
            mIlWrite.Emit(OpCodes.Ldfld, cd.mFieldInfo);    // >< 5:DateTime/... value
            mIlWrite.Emit(OpCodes.Call, writeXXX);

            var readXXX = this.GetType().GetMethod(
                readMethodName,
                BindingFlags.NonPublic | BindingFlags.Static);

            if (readXXX == null)
            {
                throw new Exception(string.Format("Unknown Method : {0}.", readMethodName));
            }

            //void ReadXXX(
            mIlRead.Emit(OpCodes.Ldarg_2);              // <  Record
            mIlRead.Emit(OpCodes.Ldarg_0);              // << 2:dbfTable
            mIlRead.Emit(OpCodes.Ldarg_1);              // << 0:Byte[]
            mIlRead.Emit(OpCodes.Ldc_I4, cd.mOffset);   // << 1:Offset // for speed
            mIlRead.Emit(OpCodes.Ldc_I4, cd.mWidth);    // << 2:Length // for speed
            mIlRead.Emit(OpCodes.Call, readXXX);
            mIlRead.Emit(OpCodes.Stfld, cd.mFieldInfo); // >< 5:DateTime/... value
        }
        private void AddColumn(FieldInfo fieldInfo, RecordAttribute recordAttribute)
        {
            // not sure whether it is more convenient for the user to inherit or not
            var atts = fieldInfo.GetCustomAttributes(typeof(ColumnAttribute), true);

            ColumnAttribute column = null;

            if (atts.Length == 0)
            {
                var fm = recordAttribute.FieldMapping;
                if (fieldInfo.IsPublic)
                {
                    if ((fm & FieldMapping.PublicFields) == 0)
                    {
                        return;
                    }
                }
                else
                {
                    if ((fm & FieldMapping.PrivateFields) == 0)
                    {
                        return;
                    }
                }
            }
            else
            {
                column = (ColumnAttribute)atts[0];
            }
            ColumnDefinition cd = null;

            if (mCreateColumns)
            {
                cd = new ColumnDefinition();
                cd.Initialize(mVersion, fieldInfo, column);
                mColumns.Add(cd);
            }
            else if (column != null && column.Type == ColumnType.DELETED_FLAG)
            {
                cd = new ColumnDefinition();
                cd.Initialize(mVersion, fieldInfo, column);
                mColumns.Insert(0, cd);
            }
            else
            {
                bool found = false;
                for (int i = 0; i < mColumns.Count; i++)
                {
                    cd = mColumns[i];
                    if (fieldInfo.Name == cd.mColumnName)
                    {
                        cd.mFieldInfo = fieldInfo;
                        found         = true;
                        break;
                    }
                }
                if (found == false && mIgnoreMissingFields == false)
                {
                    throw new Exception(string.Format("Column {0} was not found in existing DBF file", fieldInfo.Name));
                }
            }

            if (cd.mWidth == 0)
            {
                mIsFixedRecordWidth = false;
            }
        }