예제 #1
0
        public void SerializeMetadata(BlobBuilder builder, Func<BlobBuilder, ContentId> idProvider, out ContentId contentId)
        {
            SerializeMetadataImpl(builder, methodBodyStreamRva: 0, mappedFieldDataStreamRva: 0);

            contentId = idProvider(builder);

            // fill in the id:
            var idWriter = new BlobWriter(_pdbIdBlob);
            idWriter.WriteBytes(contentId.Guid);
            idWriter.WriteBytes(contentId.Stamp);
            Debug.Assert(idWriter.RemainingBytes == 0);
        }
예제 #2
0
        /// <summary>
        /// Implements <see cref="ICmsSource.FetchContentAsync(ContentId, Atom, DateTime, ICacheParams)"/>
        /// </summary>
        public async Task <Content> FetchContentAsync(ContentId id, Atom isoLang, DateTime utcNow, ICacheParams caching)
        {
            ensureOperationalState();
            var appliedIsoLang = ComponentDirector.DefaultGlobalLanguage.ISO; //in future this can be moved to property per portal

            if (isoLang.IsZero)
            {
                isoLang = appliedIsoLang;
            }

            var dirPath = m_FS.CombinePaths(m_FSRootPath, id.Portal, id.Namespace);

            using (var session = m_FS.StartSession(m_FSConnectParams))
            {
                var dir = await session.GetItemAsync(dirPath).ConfigureAwait(false) as FileSystemDirectory;

                if (dir == null)
                {
                    return(null);    //directory not found
                }
                //1st try to get language-specific file
                var(fname, fext) = getFileNameWithLangIso(id.Block, isoLang);
                var actualIsoLang = isoLang;

                var file = await dir.GetFileAsync(fname).ConfigureAwait(false);

                //2nd try to get language-agnostic file
                if (file == null)
                {
                    fname = id.Block;//without the language
                    file  = await dir.GetFileAsync(fname).ConfigureAwait(false);
                }
                else
                {
                    appliedIsoLang = isoLang;
                }

                if (file == null)
                {
                    return(null);     //file not found
                }
                var ctp = App.GetContentTypeMappings().MapFileExtension(fext);

                byte[] binContent = null;
                string txtContent = null;

                if (ctp.IsBinary)
                {
                    using (var ms = new MemoryStream())
                        using (var stream = file.FileStream)
                        {
                            await stream.CopyToAsync(ms).ConfigureAwait(false);

                            binContent = ms.ToArray();
                        }
                }
                else
                {
                    txtContent = await file.ReadAllTextAsync().ConfigureAwait(false);
                }

                var createUser = m_FS.InstanceCapabilities.SupportsCreationUserNames      ? file.CreationUser.Name     : null;
                var modifyUser = m_FS.InstanceCapabilities.SupportsModificationUserNames  ? file.ModificationUser.Name : null;
                var createDate = m_FS.InstanceCapabilities.SupportsCreationTimestamps     ? file.CreationTimestamp     : null;
                var modifyDate = m_FS.InstanceCapabilities.SupportsModificationTimestamps ? file.ModificationTimestamp : null;

                var result = new Content(id,
                                         ctp.Name,
                                         txtContent,
                                         binContent,
                                         ctp.ContentType,
                                         new LangInfo(appliedIsoLang, appliedIsoLang.Value),
                                         attachmentFileName: id.Block,
                                         createUser: createUser,
                                         modifyUser: modifyUser,
                                         createDate: createDate,
                                         modifyDate: modifyDate);
                return(result);
            }
        }
예제 #3
0
파일: PeWriter.cs 프로젝트: noahfalk/roslyn
        private void WriteDebugTable(Stream peStream, SectionHeader textSection, ContentId nativePdbContentId, ContentId portablePdbContentId, MetadataSizes metadataSizes)
        {
            Debug.Assert(nativePdbContentId.IsDefault ^ portablePdbContentId.IsDefault);

            var writer = PooledBlobBuilder.GetInstance();

            // characteristics:
            writer.WriteUInt32(0);

            // PDB stamp & version
            if (portablePdbContentId.IsDefault)
            {
                writer.WriteBytes(nativePdbContentId.Stamp);
                writer.WriteUInt32(0);
            }
            else
            {
                writer.WriteBytes(portablePdbContentId.Stamp);
                writer.WriteUInt32('P' << 24 | 'M' << 16 | 0x00 << 8 | 0x01);
            }
            
            // type: 
            const int ImageDebugTypeCodeView = 2;
            writer.WriteUInt32(ImageDebugTypeCodeView);

            // size of data:
            writer.WriteUInt32((uint)ComputeSizeOfDebugDirectoryData());

            uint dataOffset = (uint)ComputeOffsetToDebugTable(metadataSizes) + ImageDebugDirectoryBaseSize;

            // PointerToRawData (RVA of the data):
            writer.WriteUInt32((uint)textSection.RelativeVirtualAddress + dataOffset);

            // AddressOfRawData (position of the data in the PE stream):
            writer.WriteUInt32((uint)textSection.PointerToRawData + dataOffset);

            writer.WriteByte((byte)'R');
            writer.WriteByte((byte)'S');
            writer.WriteByte((byte)'D');
            writer.WriteByte((byte)'S');

            // PDB id:
            writer.WriteBytes(nativePdbContentId.Guid ?? portablePdbContentId.Guid);

            // age
            writer.WriteUInt32(PdbWriter.Age);

            // UTF-8 encoded zero-terminated path to PDB
            writer.WriteUTF8(_pdbPathOpt, allowUnpairedSurrogates: true);
            writer.WriteByte(0);

            writer.WriteContentTo(peStream);
            writer.Free();
        }
예제 #4
0
        public void Serialize(BlobBuilder builder, PEDirectoriesBuilder headers, out ContentId contentId)
        {
            var serializedSections = SerializeSections();
            Blob stampFixup;

            WritePESignature(builder);
            WriteCoffHeader(builder, serializedSections, out stampFixup);
            WritePEHeader(builder, headers, serializedSections);
            WriteSectionHeaders(builder, serializedSections);
            builder.Align(FileAlignment);

            foreach (var section in serializedSections)
            {
                builder.LinkSuffix(section.Builder);
                builder.Align(FileAlignment);
            }

            contentId = IdProvider(builder);

            // patch timestamp in COFF header:
            var stampWriter = new BlobWriter(stampFixup);
            stampWriter.WriteBytes(contentId.Stamp);
            Debug.Assert(stampWriter.RemainingBytes == 0);
        }
예제 #5
0
        private readonly static byte[] s_zeroStamp = new byte[4]; // four bytes of zero

        /// <summary>
        /// Write the entire "Debug Directory (Image Only)" along with data that it points to.
        /// </summary>
        private void WriteDebugTable(Stream peStream, SectionHeader textSection, ContentId nativePdbContentId, ContentId portablePdbContentId, MetadataSizes metadataSizes)
        {
            int tableSize = ImageDebugDirectoryBaseSize;
            Debug.Assert(tableSize != 0);
            Debug.Assert(nativePdbContentId.IsDefault || portablePdbContentId.IsDefault);
            Debug.Assert(!EmitPdb || (nativePdbContentId.IsDefault ^ portablePdbContentId.IsDefault));

            var writer = PooledBlobBuilder.GetInstance();

            int dataSize = ComputeSizeOfDebugDirectoryData();
            if (this.EmitPdb)
            {
                const int IMAGE_DEBUG_TYPE_CODEVIEW = 2; // from PE spec
                uint dataOffset = (uint)(ComputeOffsetToDebugTable(metadataSizes) + tableSize);
                WriteDebugTableEntry(writer,
                    stamp: nativePdbContentId.Stamp ?? portablePdbContentId.Stamp,
                    version: portablePdbContentId.IsDefault ? (uint)0 : ('P' << 24 | 'M' << 16 | 0x01 << 8 | 0x00),
                    debugType: IMAGE_DEBUG_TYPE_CODEVIEW,
                    sizeOfData: (uint)dataSize,
                    addressOfRawData: (uint)textSection.RelativeVirtualAddress + dataOffset, // RVA of the data
                    pointerToRawData: (uint)textSection.PointerToRawData + dataOffset); // position of the data in the PE stream
            }

            if (_deterministic)
            {
                const int IMAGE_DEBUG_TYPE_NO_TIMESTAMP = 16; // from PE spec
                WriteDebugTableEntry(writer,
                    stamp: s_zeroStamp,
                    version: 0,
                    debugType: IMAGE_DEBUG_TYPE_NO_TIMESTAMP,
                    sizeOfData: 0,
                    addressOfRawData: 0,
                    pointerToRawData: 0);
            }

            // We should now have written all and precisely the data we said we'd write for the table entries.
            Debug.Assert(writer.Count == tableSize);

            // ====================
            // The following is additional data beyond the debug directory at the offset `dataOffset`
            // pointed to by the ImageDebugTypeCodeView entry.

            if (EmitPdb)
            {
                writer.WriteByte((byte)'R');
                writer.WriteByte((byte)'S');
                writer.WriteByte((byte)'D');
                writer.WriteByte((byte)'S');

                // PDB id:
                writer.WriteBytes(nativePdbContentId.Guid ?? portablePdbContentId.Guid);

                // age
                writer.WriteUInt32(PdbWriter.Age);

                // UTF-8 encoded zero-terminated path to PDB
                int pathStart = writer.Position;
                writer.WriteUTF8(_pdbPathOpt, allowUnpairedSurrogates: true);
                writer.WriteByte(0);

                // padding:
                writer.WriteBytes(0, Math.Max(0, _minPdbPath - (writer.Position - pathStart)));
            }

            // We should now have written all and precisely the data we said we'd write for the table and its data.
            Debug.Assert(writer.Count == tableSize + dataSize);

            writer.WriteContentTo(peStream);
            writer.Free();
        }
예제 #6
0
 ///<summary>
 ///        Публикует комментарий на своей или чужой стене
 ///      
 ///</summary>
 ///<returns>
 ///</returns>
 public CommentPost AddCommentSync(
     int ownerId , int postId , string text , bool fromGroup = false, long? replyToComment = null, ContentId[] attachments = null, long? stickerId = null, string @ref = "",  string guid = ""
 ) {
     var task = _parent.Executor.ExecAsync(
             _parent._reqapi.Wall.AddComment(
                 ownerId,postId,text,fromGroup,replyToComment,attachments,stickerId,@ref,guid
             )
         );
     task.Wait();
     return task.Result.Response;
 }
예제 #7
0
 ///<summary>
 ///        Публикует запись на своей или чужой стене
 ///      
 ///</summary>
 ///<returns>
 ///        После успешного выполнения возвращает идентификатор созданной записи
 ///      
 ///</returns>
 ///<param name="message">текст сообщения (является обязательным, если не задан параметр attachments)</param>
 ///<param name="attachments">список объектов, приложенных к записи</param>
 ///<param name="ownerId">идентификатор пользователя или сообщества, на стене которого должна быть опубликована запись</param>
 ///<param name="fromGroup">Опубликовать от имени группы</param>
 ///<param name="signed">у записи, размещенной от имени сообщества, будет добавлена подпись</param>
 ///<param name="friendsOnly">запись будет доступна только друзьям</param>
 ///<param name="services">список сервисов или сайтов, на которые необходимо экспортировать запись, в случае если пользователь настроил соответствующую опцию</param>
 ///<param name="publishDate">дата публикации записи в формате unixtime. Если параметр указан, публикация записи будет отложена до указанного времени.</param>
 ///<param name="lat">географическая широта отметки, заданная в градусах (от -90 до 90)</param>
 ///<param name="@long">географическая долгота отметки, заданная в градусах (от -180 до 180)</param>
 ///<param name="placeId">идентификатор места, в котором отмечен пользователь</param>
 public WallPost PostSync(
     string message = "", ContentId[] attachments = null, int? ownerId = null, bool fromGroup = false, bool signed = false, bool? friendsOnly = false, string services = "", DateTimeOffset? publishDate = null, double? lat = null, double? @long = null,  int? placeId = null
 ) {
     var task = _parent.Executor.ExecAsync(
             _parent._reqapi.Wall.Post(
                 message,attachments,ownerId,fromGroup,signed,friendsOnly,services,publishDate,lat,@long,placeId
             )
         );
     task.Wait();
     return task.Result.Response;
 }
예제 #8
0
 public int SendPeerSync(
     long peerId , string message = null, int? guid = null, double? lat = null, double? @long = null, ContentId[] attachment = null, long[] forwardMessages = null, int? stickerId = null,  long? randomId = null
 ) {
     var task = _parent.Executor.ExecAsync(
             _parent._reqapi.Messages.SendPeer(
                 peerId,message,guid,lat,@long,attachment,forwardMessages,stickerId,randomId
             )
         );
     task.Wait();
     return task.Result.Response;
 }
예제 #9
0
        public static void AddManagedSections(
            this PEBuilder peBuilder,
            PEDirectoriesBuilder peDirectoriesBuilder,
            TypeSystemMetadataSerializer metadataSerializer,
            BlobBuilder ilStream,
            BlobBuilder mappedFieldData,
            BlobBuilder managedResourceData,
            Action <BlobBuilder, PESectionLocation> nativeResourceSectionSerializer, // opt
            int strongNameSignatureSize,                                             // TODO
            int entryPointToken,
            string pdbPathOpt,                                                       // TODO
            ContentId nativePdbContentId,                                            // TODO
            ContentId portablePdbContentId,                                          // TODO
            CorFlags corFlags)
        {
            int entryPointAddress = 0;

            // .text
            peBuilder.AddSection(".text", SectionCharacteristics.MemRead | SectionCharacteristics.MemExecute | SectionCharacteristics.ContainsCode, location =>
            {
                var sectionBuilder  = new BlobBuilder();
                var metadataBuilder = new BlobBuilder();

                var metadataSizes = metadataSerializer.MetadataSizes;

                var textSection = new ManagedTextSection(
                    metadataSizes.MetadataSize,
                    ilStreamSize: ilStream.Count,
                    mappedFieldDataSize: mappedFieldData.Count,
                    resourceDataSize: managedResourceData.Count,
                    strongNameSignatureSize: strongNameSignatureSize,
                    imageCharacteristics: peBuilder.ImageCharacteristics,
                    machine: peBuilder.Machine,
                    pdbPathOpt: pdbPathOpt,
                    isDeterministic: peBuilder.IsDeterministic);

                int methodBodyStreamRva      = location.RelativeVirtualAddress + textSection.OffsetToILStream;
                int mappedFieldDataStreamRva = location.RelativeVirtualAddress + textSection.CalculateOffsetToMappedFieldDataStream();
                metadataSerializer.SerializeMetadata(metadataBuilder, methodBodyStreamRva, mappedFieldDataStreamRva);

                BlobBuilder debugTableBuilderOpt;
                if (pdbPathOpt != null || peBuilder.IsDeterministic)
                {
                    debugTableBuilderOpt = new BlobBuilder();
                    textSection.WriteDebugTable(debugTableBuilderOpt, location, nativePdbContentId, portablePdbContentId);
                }
                else
                {
                    debugTableBuilderOpt = null;
                }

                entryPointAddress = textSection.GetEntryPointAddress(location.RelativeVirtualAddress);

                textSection.Serialize(
                    sectionBuilder,
                    location.RelativeVirtualAddress,
                    entryPointToken,
                    corFlags,
                    peBuilder.ImageBase,
                    metadataBuilder,
                    ilStream,
                    mappedFieldData,
                    managedResourceData,
                    debugTableBuilderOpt);

                peDirectoriesBuilder.AddressOfEntryPoint = entryPointAddress;
                peDirectoriesBuilder.DebugTable          = textSection.GetDebugDirectoryEntry(location.RelativeVirtualAddress);
                peDirectoriesBuilder.ImportAddressTable  = textSection.GetImportAddressTableDirectoryEntry(location.RelativeVirtualAddress);
                peDirectoriesBuilder.ImportTable         = textSection.GetImportTableDirectoryEntry(location.RelativeVirtualAddress);
                peDirectoriesBuilder.CorHeaderTable      = textSection.GetCorHeaderDirectoryEntry(location.RelativeVirtualAddress);

                return(sectionBuilder);
            });

            // .rsrc
            if (nativeResourceSectionSerializer != null)
            {
                peBuilder.AddSection(".rsrc", SectionCharacteristics.MemRead | SectionCharacteristics.ContainsInitializedData, location =>
                {
                    var sectionBuilder = new BlobBuilder();
                    nativeResourceSectionSerializer(sectionBuilder, location);
                    peDirectoriesBuilder.ResourceTable = new DirectoryEntry(location.RelativeVirtualAddress, sectionBuilder.Count);
                    return(sectionBuilder);
                });
            }

            // .reloc
            if (peBuilder.Machine == Machine.I386 || peBuilder.Machine == 0)
            {
                peBuilder.AddSection(".reloc", SectionCharacteristics.MemRead | SectionCharacteristics.MemDiscardable | SectionCharacteristics.ContainsInitializedData, location =>
                {
                    var sectionBuilder = new BlobBuilder();
                    WriteRelocSection(sectionBuilder, peBuilder.Machine, entryPointAddress);

                    peDirectoriesBuilder.BaseRelocationTable = new DirectoryEntry(location.RelativeVirtualAddress, sectionBuilder.Count);
                    return(sectionBuilder);
                });
            }
        }
예제 #10
0
 public async Task<string> SendChat(
     int chatId , string message = null, int? guid = null, double? lat = null, double? @long = null, ContentId[] attachment = null, long[] forwardMessages = null, int? stickerId = null,  long? randomId = null
 ){
     return await _parent.Executor.ExecRawAsync(
         _parent._reqapi.Messages.SendChat(
                chatId,message,guid,lat,@long,attachment,forwardMessages,stickerId,randomId
         )
     ).ConfigureAwait(false);
 }
예제 #11
0
 public string GetCidReference()
 {
     return("cid:" + ContentId.Trim('<', '>'));
 }
예제 #12
0
 public string GetId()
 {
     return(ContentId.ToString());
 }
        private readonly static byte[] zeroStamp = new byte[4]; // four bytes of zero

        /// <summary>
        /// Write the entire "Debug Directory (Image Only)" along with data that it points to.
        /// </summary>
        internal void WriteDebugTable(BlobBuilder builder, PESectionLocation textSectionLocation, ContentId nativePdbContentId, ContentId portablePdbContentId)
        {
            Debug.Assert(builder.Count == 0);

            int tableSize = ImageDebugDirectoryBaseSize;

            Debug.Assert(tableSize != 0);
            Debug.Assert(nativePdbContentId.IsDefault || portablePdbContentId.IsDefault);
            Debug.Assert(!EmitPdb || (nativePdbContentId.IsDefault ^ portablePdbContentId.IsDefault));

            int dataSize = ComputeSizeOfDebugDirectoryData();

            if (EmitPdb)
            {
                const int IMAGE_DEBUG_TYPE_CODEVIEW = 2; // from PE spec
                uint      dataOffset = (uint)(ComputeOffsetToDebugTable() + tableSize);
                WriteDebugTableEntry(builder,
                                     stamp: nativePdbContentId.Stamp ?? portablePdbContentId.Stamp,
                                     version: portablePdbContentId.IsDefault ? (uint)0 : ('P' << 24 | 'M' << 16 | 0x01 << 8 | 0x00),
                                     debugType: IMAGE_DEBUG_TYPE_CODEVIEW,
                                     sizeOfData: (uint)dataSize,
                                     addressOfRawData: (uint)textSectionLocation.RelativeVirtualAddress + dataOffset, // RVA of the data
                                     pointerToRawData: (uint)textSectionLocation.PointerToRawData + dataOffset);      // position of the data in the PE stream
            }

            if (IsDeterministic)
            {
                const int IMAGE_DEBUG_TYPE_NO_TIMESTAMP = 16; // from PE spec
                WriteDebugTableEntry(builder,
                                     stamp: zeroStamp,
                                     version: 0,
                                     debugType: IMAGE_DEBUG_TYPE_NO_TIMESTAMP,
                                     sizeOfData: 0,
                                     addressOfRawData: 0,
                                     pointerToRawData: 0);
            }

            // We should now have written all and precisely the data we said we'd write for the table entries.
            Debug.Assert(builder.Count == tableSize);

            // ====================
            // The following is additional data beyond the debug directory at the offset `dataOffset`
            // pointed to by the ImageDebugTypeCodeView entry.

            if (EmitPdb)
            {
                builder.WriteByte((byte)'R');
                builder.WriteByte((byte)'S');
                builder.WriteByte((byte)'D');
                builder.WriteByte((byte)'S');

                // PDB id:
                builder.WriteBytes(nativePdbContentId.Guid ?? portablePdbContentId.Guid);

                // age
                builder.WriteUInt32(1); // TODO: allow specify for native PDBs

                // UTF-8 encoded zero-terminated path to PDB
                int pathStart = builder.Count;
                builder.WriteUTF8(PdbPathOpt, allowUnpairedSurrogates: true);
                builder.WriteByte(0);

                // padding:
                builder.WriteBytes(0, Math.Max(0, MinPdbPath - (builder.Count - pathStart)));
            }

            // We should now have written all and precisely the data we said we'd write for the table and its data.
            Debug.Assert(builder.Count == tableSize + dataSize);
        }
예제 #14
0
 public idiso(ContentId id, string isoLang)
 {
     Id      = id;
     IsoLang = IOUtils.PackISO3CodeToInt(isoLang);
 }
예제 #15
0
        public DbCommand GetDbCommand()
        {
            var cmd = new SqlCommand
            {
                CommandText = "qp_GetContentPage",
                CommandType = CommandType.StoredProcedure
            };

            if (UseSecurity)
            {
                cmd.Parameters.Add(new SqlParameter {
                    ParameterName = "@use_security", DbType = DbType.Int32, Value = "1"
                });
                cmd.Parameters.Add(new SqlParameter {
                    ParameterName = "@user_id", DbType = DbType.Decimal, Value = UserId
                });
                cmd.Parameters.Add(new SqlParameter {
                    ParameterName = "@group_id", DbType = DbType.Decimal, Value = GroupId
                });

                cmd.Parameters.Add(new SqlParameter {
                    ParameterName = "@start_level", DbType = DbType.Int32, Value = StartLevel
                });
                cmd.Parameters.Add(new SqlParameter {
                    ParameterName = "@end_level", DbType = DbType.Int32, Value = EndLevel
                });
                cmd.Parameters.Add(new SqlParameter {
                    ParameterName = "@entity_name", DbType = DbType.String, Value = "content_item"
                });
                cmd.Parameters.Add(new SqlParameter {
                    ParameterName = "@parent_entity_name", DbType = DbType.String, Value = "content"
                });
                cmd.Parameters.Add(new SqlParameter {
                    ParameterName = "@parent_entity_id", DbType = DbType.Decimal, Value = ContentId.ToString()
                });
                cmd.Parameters.Add(new SqlParameter {
                    ParameterName = "@insert_key", DbType = DbType.String, Value = InsertKey
                });
            }

            cmd.Parameters.Add(new SqlParameter {
                ParameterName = "@Select", DbType = DbType.String, Value = Select
            });
            cmd.Parameters.Add(new SqlParameter {
                ParameterName = "@From", DbType = DbType.String, Value = From
            });
            cmd.Parameters.Add(new SqlParameter {
                ParameterName = "@Where", DbType = DbType.String, Value = Utils.CleanSql(Where)
            });
            cmd.Parameters.Add(new SqlParameter {
                ParameterName = "@OrderBy", DbType = DbType.String, Value = Utils.CleanSql(OrderBy)
            });
            cmd.Parameters.Add(new SqlParameter {
                ParameterName = "@StartRow", DbType = DbType.Int32, Value = StartRow
            });
            cmd.Parameters.Add(new SqlParameter {
                ParameterName = "@PageSize", DbType = DbType.Int32, Value = PageSize
            });

            cmd.Parameters.Add(new SqlParameter {
                ParameterName = "@GetCount", DbType = DbType.Int32, Value = GetCount
            });
            cmd.Parameters.Add(new SqlParameter {
                ParameterName = "@TotalRecords", DbType = DbType.Int32, Direction = ParameterDirection.Output
            });

            return(cmd);
        }
예제 #16
0
 public void SetBroadcastSync(
     ContentId audio , params int[] targetIds 
 ) {
     var task = _parent.Executor.ExecAsync(
             _parent._reqapi.Audio.SetBroadcast(
                 audio,targetIds
             )
         );
     task.Wait();
     
 }
예제 #17
0
 public async Task <int> SendPeer(
     long peerId , string message = null, int? guid = null, double? lat = null, double? @long = null, ContentId[] attachment = null, long[] forwardMessages = null, int? stickerId = null,  long? randomId = null
 ) {
     return (
         await _parent.Executor.ExecAsync(
             _parent._reqapi.Messages.SendPeer(
                 peerId,message,guid,lat,@long,attachment,forwardMessages,stickerId,randomId
             )
         ).ConfigureAwait(false)
     ).Response;
 }
예제 #18
0
        public void SerializeMetadata(BlobBuilder builder, Func <BlobBuilder, ContentId> idProvider, out ContentId contentId)
        {
            SerializeMetadataImpl(builder, methodBodyStreamRva: 0, mappedFieldDataStreamRva: 0);

            contentId = idProvider(builder);

            // fill in the id:
            var idWriter = new BlobWriter(_pdbIdBlob);

            idWriter.WriteBytes(contentId.Guid);
            idWriter.WriteBytes(contentId.Stamp);
            Debug.Assert(idWriter.RemainingBytes == 0);
        }
예제 #19
0
 ///<summary>
 ///        Публикует запись на своей или чужой стене
 ///      
 ///</summary>
 ///<returns>
 ///        После успешного выполнения возвращает идентификатор созданной записи
 ///      
 ///</returns>
 ///<param name="message">текст сообщения (является обязательным, если не задан параметр attachments)</param>
 ///<param name="attachments">список объектов, приложенных к записи</param>
 ///<param name="ownerId">идентификатор пользователя или сообщества, на стене которого должна быть опубликована запись</param>
 ///<param name="fromGroup">Опубликовать от имени группы</param>
 ///<param name="signed">у записи, размещенной от имени сообщества, будет добавлена подпись</param>
 ///<param name="friendsOnly">запись будет доступна только друзьям</param>
 ///<param name="services">список сервисов или сайтов, на которые необходимо экспортировать запись, в случае если пользователь настроил соответствующую опцию</param>
 ///<param name="publishDate">дата публикации записи в формате unixtime. Если параметр указан, публикация записи будет отложена до указанного времени.</param>
 ///<param name="lat">географическая широта отметки, заданная в градусах (от -90 до 90)</param>
 ///<param name="@long">географическая долгота отметки, заданная в градусах (от -180 до 180)</param>
 ///<param name="placeId">идентификатор места, в котором отмечен пользователь</param>
 public async Task <WallPost> Post(
     string message = "", ContentId[] attachments = null, int? ownerId = null, bool fromGroup = false, bool signed = false, bool? friendsOnly = false, string services = "", DateTimeOffset? publishDate = null, double? lat = null, double? @long = null,  int? placeId = null
 ) {
     return (
         await _parent.Executor.ExecAsync(
             _parent._reqapi.Wall.Post(
                 message,attachments,ownerId,fromGroup,signed,friendsOnly,services,publishDate,lat,@long,placeId
             )
         ).ConfigureAwait(false)
     ).Response;
 }
예제 #20
0
            public Request<int> SendPeer(
                long peerId , string message = null, int? guid = null, double? lat = null, double? @long = null, ContentId[] attachment = null, long[] forwardMessages = null, int? stickerId = null,  long? randomId = null
            ) {
                var req = new Request<int>{
                    MethodName = "messages.send",
                    Parameters = new Dictionary<string, string> {

                        { "peer_id", peerId.ToNCString()},
                        { "message", message},
                        { "guid", MiscTools.NullableString(guid)},
                        { "lat", MiscTools.NullableString(lat)},
                        { "long", MiscTools.NullableString(@long)},
                        { "attachment", (attachment??new ContentId[]{}).ToNCStringA()},
                        { "forward_messages", (forwardMessages??new long[]{}).ToNCStringA()},
                        { "sticker_id", MiscTools.NullableString(stickerId)},
                        { "random_id", MiscTools.NullableString(randomId)},

                    }
                };
                    req.Token = _parent.CurrentToken;
                return req;
            }
예제 #21
0
 ///<summary>
 ///        Публикует комментарий на своей или чужой стене
 ///      
 ///</summary>
 ///<returns>
 ///</returns>
 public async Task <CommentPost> AddComment(
     int ownerId , int postId , string text , bool fromGroup = false, long? replyToComment = null, ContentId[] attachments = null, long? stickerId = null, string @ref = "",  string guid = ""
 ) {
     return (
         await _parent.Executor.ExecAsync(
             _parent._reqapi.Wall.AddComment(
                 ownerId,postId,text,fromGroup,replyToComment,attachments,stickerId,@ref,guid
             )
         ).ConfigureAwait(false)
     ).Response;
 }
예제 #22
0
            ///<summary>
            ///        Публикует запись на своей или чужой стене
            ///      
            ///</summary>
            ///<returns>
            ///        После успешного выполнения возвращает идентификатор созданной записи
            ///      
            ///</returns>
            ///<param name="message">текст сообщения (является обязательным, если не задан параметр attachments)</param>
            ///<param name="attachments">список объектов, приложенных к записи</param>
            ///<param name="ownerId">идентификатор пользователя или сообщества, на стене которого должна быть опубликована запись</param>
            ///<param name="fromGroup">Опубликовать от имени группы</param>
            ///<param name="signed">у записи, размещенной от имени сообщества, будет добавлена подпись</param>
            ///<param name="friendsOnly">запись будет доступна только друзьям</param>
            ///<param name="services">список сервисов или сайтов, на которые необходимо экспортировать запись, в случае если пользователь настроил соответствующую опцию</param>
            ///<param name="publishDate">дата публикации записи в формате unixtime. Если параметр указан, публикация записи будет отложена до указанного времени.</param>
            ///<param name="lat">географическая широта отметки, заданная в градусах (от -90 до 90)</param>
            ///<param name="@long">географическая долгота отметки, заданная в градусах (от -180 до 180)</param>
            ///<param name="placeId">идентификатор места, в котором отмечен пользователь</param>
            public Request<WallPost> Post(
                string message = "", ContentId[] attachments = null, int? ownerId = null, bool fromGroup = false, bool signed = false, bool? friendsOnly = false, string services = "", DateTimeOffset? publishDate = null, double? lat = null, double? @long = null,  int? placeId = null
            ) {
                var req = new Request<WallPost>{
                    MethodName = "wall.post",
                    Parameters = new Dictionary<string, string> {

                        { "message", message},
                        { "attachments", (attachments??new ContentId[]{}).ToNCStringA()},
                        { "owner_id", MiscTools.NullableString(ownerId)},
                        { "from_group", (fromGroup?1:0).ToNCString()},
                        { "signed", (signed?1:0).ToNCString()},
                        { "friends_only", (friendsOnly != null ? ( friendsOnly.Value ? 1 : 0 ).ToNCString() : "")},
                        { "services", services},
                        { "publish_date", MiscTools.NullableString(publishDate?.ToUnixTimeSeconds())},
                        { "lat", MiscTools.NullableString(lat)},
                        { "long", MiscTools.NullableString(@long)},
                        { "place_id", MiscTools.NullableString(placeId)},

                    }
                };
                    req.Token = _parent.CurrentToken;
                return req;
            }
예제 #23
0
            ///<summary>
            ///        Публикует комментарий на своей или чужой стене
            ///      
            ///</summary>
            ///<returns>
            ///</returns>
            public Request<CommentPost> AddComment(
                int ownerId , int postId , string text , bool fromGroup = false, long? replyToComment = null, ContentId[] attachments = null, long? stickerId = null, string @ref = "",  string guid = ""
            ) {
                var req = new Request<CommentPost>{
                    MethodName = "wall.addComment",
                    Parameters = new Dictionary<string, string> {

                        { "owner_id", ownerId.ToNCString()},
                        { "post_id", postId.ToNCString()},
                        { "text", text},
                        { "from_group", (fromGroup?1:0).ToNCString()},
                        { "reply_to_comment", MiscTools.NullableString(replyToComment)},
                        { "attachments", (attachments??new ContentId[]{}).ToNCStringA()},
                        { "sticker_id", MiscTools.NullableString(stickerId)},
                        { "ref", @ref},
                        { "guid", guid},

                    }
                };
                    req.Token = _parent.CurrentToken;
                return req;
            }
예제 #24
0
            public Request<bool> SetBroadcast(
                ContentId audio , params int[] targetIds 
            ) {
                var req = new Request<bool>{
                    MethodName = "audio.setBroadcast",
                    Parameters = new Dictionary<string, string> {

                        { "audio",  audio.ToIdString() },
                        { "target_ids", (targetIds??new int[]{}).ToNCStringA()},

                    }
                };
                    req.Token = _parent.CurrentToken;
                return req;
            }
예제 #25
0
        private readonly static byte[] zeroStamp = new byte[4]; // four bytes of zero

        /// <summary>
        /// Write the entire "Debug Directory (Image Only)" along with data that it points to.
        /// </summary>
        internal void WriteDebugTable(BlobBuilder builder, PESectionLocation textSectionLocation, ContentId nativePdbContentId, ContentId portablePdbContentId)
        {
            Debug.Assert(builder.Count == 0);

            int tableSize = ImageDebugDirectoryBaseSize;
            Debug.Assert(tableSize != 0);
            Debug.Assert(nativePdbContentId.IsDefault || portablePdbContentId.IsDefault);
            Debug.Assert(!EmitPdb || (nativePdbContentId.IsDefault ^ portablePdbContentId.IsDefault));

            int dataSize = ComputeSizeOfDebugDirectoryData();
            if (EmitPdb)
            {
                const int IMAGE_DEBUG_TYPE_CODEVIEW = 2; // from PE spec
                uint dataOffset = (uint)(ComputeOffsetToDebugTable() + tableSize);
                WriteDebugTableEntry(builder,
                    stamp: nativePdbContentId.Stamp ?? portablePdbContentId.Stamp,
                    version: portablePdbContentId.IsDefault ? (uint)0 : ('P' << 24 | 'M' << 16 | 0x01 << 8 | 0x00),
                    debugType: IMAGE_DEBUG_TYPE_CODEVIEW,
                    sizeOfData: (uint)dataSize,
                    addressOfRawData: (uint)textSectionLocation.RelativeVirtualAddress + dataOffset, // RVA of the data
                    pointerToRawData: (uint)textSectionLocation.PointerToRawData + dataOffset); // position of the data in the PE stream
            }

            if (IsDeterministic)
            {
                const int IMAGE_DEBUG_TYPE_NO_TIMESTAMP = 16; // from PE spec
                WriteDebugTableEntry(builder,
                    stamp: zeroStamp,
                    version: 0,
                    debugType: IMAGE_DEBUG_TYPE_NO_TIMESTAMP,
                    sizeOfData: 0,
                    addressOfRawData: 0,
                    pointerToRawData: 0);
            }

            // We should now have written all and precisely the data we said we'd write for the table entries.
            Debug.Assert(builder.Count == tableSize);

            // ====================
            // The following is additional data beyond the debug directory at the offset `dataOffset`
            // pointed to by the ImageDebugTypeCodeView entry.

            if (EmitPdb)
            {
                builder.WriteByte((byte)'R');
                builder.WriteByte((byte)'S');
                builder.WriteByte((byte)'D');
                builder.WriteByte((byte)'S');

                // PDB id:
                builder.WriteBytes(nativePdbContentId.Guid ?? portablePdbContentId.Guid);

                // age
                builder.WriteUInt32(1); // TODO: allow specify for native PDBs

                // UTF-8 encoded zero-terminated path to PDB
                int pathStart = builder.Count;
                builder.WriteUTF8(PdbPathOpt, allowUnpairedSurrogates: true);
                builder.WriteByte(0);

                // padding:
                builder.WriteBytes(0, Math.Max(0, MinPdbPath - (builder.Count - pathStart)));
            }

            // We should now have written all and precisely the data we said we'd write for the table and its data.
            Debug.Assert(builder.Count == tableSize + dataSize);
        }
예제 #26
0
        public static void AddManagedSections(
            this PEBuilder peBuilder,
            PEDirectoriesBuilder peDirectoriesBuilder,
            TypeSystemMetadataSerializer metadataSerializer,
            BlobBuilder ilStream,
            BlobBuilder mappedFieldData,
            BlobBuilder managedResourceData,
            Action<BlobBuilder, PESectionLocation> nativeResourceSectionSerializer, // opt
            int strongNameSignatureSize, // TODO
            int entryPointToken,
            string pdbPathOpt, // TODO
            ContentId nativePdbContentId, // TODO
            ContentId portablePdbContentId, // TODO
            CorFlags corFlags)
        {
            int entryPointAddress = 0;

            // .text
            peBuilder.AddSection(".text", SectionCharacteristics.MemRead | SectionCharacteristics.MemExecute | SectionCharacteristics.ContainsCode, location =>
            {
                var sectionBuilder = new BlobBuilder();
                var metadataBuilder = new BlobBuilder();

                var metadataSizes = metadataSerializer.MetadataSizes;

                var textSection = new ManagedTextSection(
                    metadataSizes.MetadataSize,
                    ilStreamSize: ilStream.Count,
                    mappedFieldDataSize: mappedFieldData.Count,
                    resourceDataSize: managedResourceData.Count,
                    strongNameSignatureSize: strongNameSignatureSize,
                    imageCharacteristics: peBuilder.ImageCharacteristics,
                    machine: peBuilder.Machine,
                    pdbPathOpt: pdbPathOpt,
                    isDeterministic: peBuilder.IsDeterministic);

                int methodBodyStreamRva = location.RelativeVirtualAddress + textSection.OffsetToILStream;
                int mappedFieldDataStreamRva = location.RelativeVirtualAddress + textSection.CalculateOffsetToMappedFieldDataStream();
                metadataSerializer.SerializeMetadata(metadataBuilder, methodBodyStreamRva, mappedFieldDataStreamRva);

                BlobBuilder debugTableBuilderOpt;
                if (pdbPathOpt != null || peBuilder.IsDeterministic)
                {
                    debugTableBuilderOpt = new BlobBuilder();
                    textSection.WriteDebugTable(debugTableBuilderOpt, location, nativePdbContentId, portablePdbContentId);
                }
                else
                {
                    debugTableBuilderOpt = null;
                }

                entryPointAddress = textSection.GetEntryPointAddress(location.RelativeVirtualAddress);

                textSection.Serialize(
                    sectionBuilder,
                    location.RelativeVirtualAddress,
                    entryPointToken,
                    corFlags,
                    peBuilder.ImageBase,
                    metadataBuilder,
                    ilStream,
                    mappedFieldData,
                    managedResourceData,
                    debugTableBuilderOpt);

                peDirectoriesBuilder.AddressOfEntryPoint = entryPointAddress;
                peDirectoriesBuilder.DebugTable = textSection.GetDebugDirectoryEntry(location.RelativeVirtualAddress);
                peDirectoriesBuilder.ImportAddressTable = textSection.GetImportAddressTableDirectoryEntry(location.RelativeVirtualAddress);
                peDirectoriesBuilder.ImportTable = textSection.GetImportTableDirectoryEntry(location.RelativeVirtualAddress);
                peDirectoriesBuilder.CorHeaderTable = textSection.GetCorHeaderDirectoryEntry(location.RelativeVirtualAddress);

                return sectionBuilder;
            });

            // .rsrc
            if (nativeResourceSectionSerializer != null)
            {
                peBuilder.AddSection(".rsrc", SectionCharacteristics.MemRead | SectionCharacteristics.ContainsInitializedData, location => 
                {
                    var sectionBuilder = new BlobBuilder();
                    nativeResourceSectionSerializer(sectionBuilder, location);
                    peDirectoriesBuilder.ResourceTable = new DirectoryEntry(location.RelativeVirtualAddress, sectionBuilder.Count);
                    return sectionBuilder;
                });
            }

            // .reloc
            if (peBuilder.Machine == Machine.I386 || peBuilder.Machine == 0)
            {
                peBuilder.AddSection(".reloc", SectionCharacteristics.MemRead | SectionCharacteristics.MemDiscardable | SectionCharacteristics.ContainsInitializedData, location =>
                {
                    var sectionBuilder = new BlobBuilder();
                    WriteRelocSection(sectionBuilder, peBuilder.Machine, entryPointAddress);

                    peDirectoriesBuilder.BaseRelocationTable = new DirectoryEntry(location.RelativeVirtualAddress, sectionBuilder.Count);
                    return sectionBuilder;
                });
            }
        }
예제 #27
0
파일: PeWriter.cs 프로젝트: noahfalk/roslyn
        private void WriteTextSection(
            Stream peStream,
            SectionHeader textSection,
            int importTableRva,
            int importAddressTableRva,
            int entryPointToken,
            BlobBuilder metadataWriter,
            BlobBuilder ilWriter,
            BlobBuilder mappedFieldDataWriter,
            BlobBuilder managedResourceWriter,
            MetadataSizes metadataSizes,
            ContentId nativePdbContentId,
            ContentId portablePdbContentId,
            out long metadataPosition)
        {
            // TODO: zero out all bytes:
            peStream.Position = textSection.PointerToRawData;

            if (_properties.RequiresStartupStub)
            {
                WriteImportAddressTable(peStream, importTableRva);
            }

            var corHeader = CreateCorHeader(metadataSizes, textSection.RelativeVirtualAddress, entryPointToken);
            WriteCorHeader(peStream, corHeader);

            // IL:
            ilWriter.Align(4);
            ilWriter.WriteContentTo(peStream);

            // metadata:
            metadataPosition = peStream.Position;
            Debug.Assert(metadataWriter.Count % 4 == 0);
            metadataWriter.WriteContentTo(peStream);

            // managed resources:
            Debug.Assert(managedResourceWriter.Count % 4 == 0);
            managedResourceWriter.WriteContentTo(peStream);

            // strong name signature:
            WriteSpaceForHash(peStream, metadataSizes.StrongNameSignatureSize);

            if (EmitPdb)
            {
                WriteDebugTable(peStream, textSection, nativePdbContentId, portablePdbContentId, metadataSizes);
            }

            if (_properties.RequiresStartupStub)
            {
                WriteImportTable(peStream, importTableRva, importAddressTableRva);
                WriteNameTable(peStream);
                WriteRuntimeStartupStub(peStream, importAddressTableRva);
            }

            // mapped field data:            
            mappedFieldDataWriter.WriteContentTo(peStream);

            // TODO: zero out all bytes:
            int alignedPosition = textSection.PointerToRawData + textSection.SizeOfRawData;
            if (peStream.Position != alignedPosition)
            {
                peStream.Position = alignedPosition - 1;
                peStream.WriteByte(0);
            }
        }
예제 #28
0
 public async Task  SetBroadcast(
     ContentId audio , params int[] targetIds 
 ) {
         await _parent.Executor.ExecAsync(
             _parent._reqapi.Audio.SetBroadcast(
                 audio,targetIds
             )
         ).ConfigureAwait(false)
     ;
 }
예제 #29
0
파일: PeWriter.cs 프로젝트: noahfalk/roslyn
        private bool WritePeToStream(MetadataWriter mdWriter, Func<Stream> getPeStream, Func<Stream> getPortablePdbStreamOpt, PdbWriter nativePdbWriterOpt)
        {
            // TODO: we can precalculate the exact size of IL stream
            var ilWriter = new BlobBuilder(32 * 1024);
            var metadataWriter = new BlobBuilder(16 * 1024);
            var mappedFieldDataWriter = new BlobBuilder();
            var managedResourceWriter = new BlobBuilder(1024);

            var debugMetadataWriterOpt = (getPortablePdbStreamOpt != null) ? new BlobBuilder(16 * 1024) : null;

            nativePdbWriterOpt?.SetMetadataEmitter(mdWriter);

            // Since we are producing a full assembly, we should not have a module version ID
            // imposed ahead-of time. Instead we will compute a deterministic module version ID
            // based on the contents of the generated stream.
            Debug.Assert(_properties.PersistentIdentifier == default(Guid));

            int sectionCount = 1;
            if (_properties.RequiresStartupStub) sectionCount++; //.reloc
            if (!IteratorHelper.EnumerableIsEmpty(_nativeResourcesOpt) || _nativeResourceSectionOpt != null) sectionCount++; //.rsrc;

            int sizeOfPeHeaders = ComputeSizeOfPeHeaders(sectionCount);
            int textSectionRva = BitArithmeticUtilities.Align(sizeOfPeHeaders, _properties.SectionAlignment);

            int moduleVersionIdOffsetInMetadataStream;
            int methodBodyStreamRva = textSectionRva + OffsetToILStream;

            int entryPointToken;
            MetadataSizes metadataSizes;
            mdWriter.SerializeMetadataAndIL(
                metadataWriter,
                debugMetadataWriterOpt,
                nativePdbWriterOpt,
                ilWriter,
                mappedFieldDataWriter,
                managedResourceWriter,
                methodBodyStreamRva,
                mdSizes => CalculateMappedFieldDataStreamRva(textSectionRva, mdSizes),
                out moduleVersionIdOffsetInMetadataStream,
                out entryPointToken,
                out metadataSizes);

            ContentId nativePdbContentId;
            if (nativePdbWriterOpt != null)
            {
                var assembly = mdWriter.Module.AsAssembly;
                if (assembly != null && assembly.Kind == OutputKind.WindowsRuntimeMetadata)
                {
                    // Dev12: If compiling to winmdobj, we need to add to PDB source spans of
                    //        all types and members for better error reporting by WinMDExp.
                    nativePdbWriterOpt.WriteDefinitionLocations(mdWriter.Module.GetSymbolToLocationMap());
                }
                else
                {
#if DEBUG
                    // validate that all definitions are writable
                    // if same scenario would happen in an winmdobj project
                    nativePdbWriterOpt.AssertAllDefinitionsHaveTokens(mdWriter.Module.GetSymbolToLocationMap());
#endif
                }

                nativePdbContentId = nativePdbWriterOpt.GetContentId();

                // the writer shall not be used after this point for writing:
                nativePdbWriterOpt = null;
            }
            else
            {
                nativePdbContentId = default(ContentId);
            }
            
            // write to Portable PDB stream:
            ContentId portablePdbContentId;
            Stream portablePdbStream = getPortablePdbStreamOpt?.Invoke();
            if (portablePdbStream != null)
            {
                debugMetadataWriterOpt.WriteContentTo(portablePdbStream);

                if (_deterministic)
                {
                    portablePdbContentId = ContentId.FromHash(CryptographicHashProvider.ComputeSha1(portablePdbStream));
                }
                else
                {
                    portablePdbContentId = new ContentId(Guid.NewGuid().ToByteArray(), BitConverter.GetBytes(_timeStamp));
                }
            }
            else
            {
                portablePdbContentId = default(ContentId);
            }

            // Only the size of the fixed part of the debug table goes here.
            DirectoryEntry debugDirectory = default(DirectoryEntry);
            DirectoryEntry importTable = default(DirectoryEntry);
            DirectoryEntry importAddressTable = default(DirectoryEntry);
            int entryPointAddress = 0;

            if (EmitPdb)
            {
                debugDirectory = new DirectoryEntry(textSectionRva + ComputeOffsetToDebugTable(metadataSizes), ImageDebugDirectoryBaseSize);
            }

            if (_properties.RequiresStartupStub)
            {
                importAddressTable = new DirectoryEntry(textSectionRva, SizeOfImportAddressTable);
                entryPointAddress = CalculateMappedFieldDataStreamRva(textSectionRva, metadataSizes) - (_is32bit ? 6 : 10); // TODO: constants
                importTable = new DirectoryEntry(textSectionRva + ComputeOffsetToImportTable(metadataSizes), (_is32bit ? 66 : 70) + 13); // TODO: constants
            }

            var corHeaderDirectory = new DirectoryEntry(textSectionRva + SizeOfImportAddressTable, size: CorHeaderSize);

            long ntHeaderTimestampPosition;
            long metadataPosition;

            List<SectionHeader> sectionHeaders = CreateSectionHeaders(metadataSizes, sectionCount);

            CoffHeader coffHeader;
            NtHeader ntHeader;
            FillInNtHeader(sectionHeaders, entryPointAddress, corHeaderDirectory, importTable, importAddressTable, debugDirectory, out coffHeader, out ntHeader);

            Stream peStream = getPeStream();
            if (peStream == null)
            {
                return false;
            }

            WriteHeaders(peStream, ntHeader, coffHeader, sectionHeaders, out ntHeaderTimestampPosition);

            WriteTextSection(
                peStream,
                sectionHeaders[0],
                importTable.RelativeVirtualAddress,
                importAddressTable.RelativeVirtualAddress,
                entryPointToken,
                metadataWriter,
                ilWriter,
                mappedFieldDataWriter,
                managedResourceWriter,
                metadataSizes,
                nativePdbContentId,
                portablePdbContentId,
                out metadataPosition);

            var resourceSection = sectionHeaders.FirstOrDefault(s => s.Name == ResourceSectionName);
            if (resourceSection != null)
            {
                WriteResourceSection(peStream, resourceSection);
            }

            var relocSection = sectionHeaders.FirstOrDefault(s => s.Name == RelocationSectionName);
            if (relocSection != null)
            {
                WriteRelocSection(peStream, relocSection, entryPointAddress);
            }

            if (_deterministic)
            {
                var mvidPosition = metadataPosition + moduleVersionIdOffsetInMetadataStream;
                WriteDeterministicGuidAndTimestamps(peStream, mvidPosition, ntHeaderTimestampPosition);
            }

            return true;
        }
예제 #30
0
 public idiso(ContentId id, Atom isoLang)
 {
     Id      = id;
     IsoLang = isoLang;
 }