Sdílet prostřednictvím


Důležité informace o zabezpečení pro data

Při práci s daty ve Službě Windows Communication Foundation (WCF) musíte zvážit řadu kategorií hrozeb. Následující seznam ukazuje nejdůležitější třídy hrozeb, které souvisejí se zpracováním dat. WCF poskytuje nástroje pro zmírnění těchto hrozeb.

  • Odepření služby

    Při příjmu nedůvěryhodných dat mohou tato data způsobit, že přijímající strana přistupuje k nepřiměřeně velkému množství různých prostředků, jako jsou paměť, vlákna, dostupná připojení nebo cykly procesoru, což způsobí zdlouhavé výpočty. Útok na dostupnost služby na server může způsobit chybové ukončení a nemůže zpracovávat zprávy z jiných legitimních klientů.

  • Spuštění škodlivého kódu

    Příchozí nedůvěryhodná data způsobí, že přijímající strana spustí kód, který neměl v úmyslu.

  • Zveřejnění informací

    Vzdálený útočník vynutí přijímající stranu reagovat na své žádosti takovým způsobem, aby zveřejnil více informací, než chce.

Zabezpečení přístupu kódu a kódu poskytnutého uživatelem

Řada míst v infrastruktuře Wcf (Windows Communication Foundation) spouští kód, který poskytuje uživatel. Modul serializace může například DataContractSerializer volat přístupové objekty a get přístupové objekty vlastností set poskytované uživatelem. Infrastruktura kanálu WCF může také volat uživatelem poskytované odvozené třídy Message třídy.

Autor kódu zodpovídá za to, aby se zajistilo, že neexistují žádná ohrožení zabezpečení. Pokud například vytvoříte typ datového kontraktu s vlastností datového člena typu integer a v set implementaci přístupového objektu přidělíte pole na základě hodnoty vlastnosti, zpřístupníte možnost útoku do služby, pokud škodlivá zpráva obsahuje extrémně velkou hodnotu pro tohoto datového člena. Obecně se vyhněte přidělení na základě příchozích dat nebo zdlouhavého zpracování v uživatelském kódu (zejména v případě, že může být zdlouhavé zpracování způsobeno malým množstvím příchozích dat). Při analýze zabezpečení uživatelského kódu nezapomeňte vzít v úvahu také všechny případy selhání (to znamená všechny větve kódu, ve kterých jsou vyvolány výjimky).

Konečným příkladem uživatelem poskytnutého kódu je kód uvnitř vaší implementace služby pro každou operaci. Zabezpečení implementace služby je vaší zodpovědností. Nechtěně vytvářet nezabezpečené implementace operací, které můžou vést k ohrožení zabezpečení dosazení služby, je snadné. Například operace, která přebírá řetězec a vrací seznam zákazníků z databáze, jejíž název začíná tímto řetězcem. Pokud pracujete s velkou databází a předávaný řetězec je jen jedno písmeno, může se váš kód pokusit vytvořit zprávu větší než veškerá dostupná paměť, což způsobí selhání celé služby. (V OutOfMemoryException rozhraní .NET Framework není možné obnovit a vždy dojde k ukončení aplikace.)

Měli byste zajistit, aby do různých bodů rozšiřitelnosti nebyl zapojen žádný škodlivý kód. To je zvlášť důležité, když běží pod částečným vztahem důvěryhodnosti, pracuje s typy z částečně důvěryhodných sestavení nebo vytváří součásti použitelné částečně důvěryhodným kódem. Další informace najdete v části "Částečné hrozby důvěryhodnosti" v další části.

Všimněte si, že při spuštění v částečné důvěryhodnosti podporuje infrastruktura serializace kontraktů dat pouze omezenou podmnožinu programovacího modelu kontraktu dat – například soukromé datové členy nebo typy používající SerializableAttribute atribut nejsou podporovány. Další informace naleznete v tématu Částečná důvěryhodnost.

Poznámka:

Zabezpečení přístupu kódu (CAS) je zastaralé ve všech verzích rozhraní .NET Framework a .NET. Nedávné verze rozhraní .NET nedotknou poznámek CAS a generují chyby, pokud se používají rozhraní API související s casem. Vývojáři by měli hledat alternativní způsoby provádění úloh zabezpečení.

Zabránění neúmyslnému zpřístupnění informací

Při navrhování serializovatelnýchtypůch

Zvažte následující skutečnosti:

  • DataContractSerializer Programovací model umožňuje vystavení privátních a interních dat mimo typ nebo sestavení během serializace. Kromě toho lze během exportu schématu vystavit tvar typu. Nezapomeňte porozumět projekci serializace vašeho typu. Pokud nechcete nic vystavit, zakažte serializaci (například použitím atributu DataMemberAttribute v případě kontraktu dat).

  • Mějte na paměti, že stejný typ může mít více projekcí serializace v závislosti na použitém serializátoru. Stejný typ může zveřejnit jednu sadu dat při použití s DataContractSerializer a jinou sadou dat při použití s XmlSerializer. Náhodné použití nesprávného serializátoru může vést ke zpřístupnění informací.

  • XmlSerializer Použití starší verze vzdáleného volání procedur (RPC)/kódovaný režim může neúmyslně vystavit obrazec grafu objektu na straně odesílání na přijímající straně.

Zabránění útokům na dostupnost služby

Kvóty

Příčinou přijímající strany přidělení značného množství paměti je potenciální útok na dostupnost služby. I když se tato část zaměřuje na problémy se spotřebou paměti vyplývající z velkých zpráv, mohou nastat jiné útoky. Zprávy mohou například používat nepřiměřenou dobu zpracování.

Útoky na dostupnost služby se obvykle zmírňují pomocí kvót. Při překročení QuotaExceededException kvóty se obvykle vyvolá výjimka. Bez kvóty může škodlivá zpráva způsobit přístup k veškeré dostupné paměti, což vede k výjimce OutOfMemoryException nebo všem dostupným zásobníkům, což vede StackOverflowExceptionk .

Scénář překročení kvóty je možné obnovit; pokud dojde ke spuštěné službě, zpráva, která se právě zpracovává, se zahodí a služba udržuje spuštěné a zpracovává další zprávy. Scénáře přetečení zásobníku a nedostatku paměti ale nejsou v rozhraní .NET Framework obnovitelné. služba se ukončí, pokud dojde k těmto výjimkám.

Kvóty ve WCF nezahrnují žádné předběžné přidělení. Pokud je například kvóta (nalezená MaxReceivedMessageSize v různých třídách) nastavena na 128 kB, neznamená to, že pro každou zprávu je automaticky přiděleno 128 kB. Skutečná přidělená částka závisí na skutečné velikosti příchozí zprávy.

V přenosové vrstvě je k dispozici mnoho kvót. Jedná se o kvóty vynucované konkrétním dopravním kanálem, který se používá (HTTP, TCP atd.). I když toto téma popisuje některé z těchto kvót, tyto kvóty jsou podrobně popsány v kvótách přenosu.

Ohrožení zabezpečení hashovací tabulky

Ohrožení zabezpečení existuje, když kontrakty dat obsahují hashtable nebo kolekce. K problému dochází, pokud je do hashovatelné tabulky vložen velký počet hodnot, kde velký počet těchto hodnot generuje stejnou hodnotu hash. To se dá použít jako útok DOS. Toto ohrožení zabezpečení je možné zmírnit nastavením kvóty vazby MaxReceivedMessageSize. Při nastavování této kvóty je potřeba věnovat pozornost, aby se zabránilo takovým útokům. Tato kvóta představuje horní limit velikosti zprávy WCF. Kromě toho nepoužívejte v kontraktech dat hashtable nebo kolekce.

Omezení spotřeby paměti bez streamování

Model zabezpečení kolem velkých zpráv závisí na tom, jestli se používá streamování. V základním nestreamovém případě se zprávy ukládají do vyrovnávací paměti. V takovém případě použijte kvótu MaxReceivedMessageSizeTransportBindingElement pro vazby poskytované systémem, abyste ochránili před velkými zprávami omezením maximální velikosti zprávy na přístup. Upozorňujeme, že služba může současně zpracovávat více zpráv, v takovém případě jsou všechny v paměti. Tuto hrozbu můžete zmírnit pomocí funkce omezování.

Všimněte si také, že MaxReceivedMessageSize neumisťuje horní mez spotřeby paměti pro jednotlivé zprávy, ale omezuje ji na konstantní faktor. Pokud je například MaxReceivedMessageSize 1 MB a přijme se zpráva o velikosti 1 MB a pak se deserializuje, vyžaduje se další paměť, aby obsahovala deserializovaný objektový graf, což vede k celkové spotřebě paměti nad 1 MB. Z tohoto důvodu se vyhněte vytváření serializovatelných typů, které by mohly vést k významné spotřebě paměti bez velkého množství příchozích dat. Například kontrakt dat "MyContract" s 50 volitelnými poli datového členu a dalších 100 privátních polí lze vytvořit instanci s konstrukcí XML "<MyContract/>". Výsledkem tohoto XML je přístupná paměť pro 150 polí. Všimněte si, že datové členy jsou ve výchozím nastavení volitelné. Problém je složený, pokud je takový typ součástí pole.

MaxReceivedMessageSize samotná není dostatečná, aby se zabránilo všem útokům na dostupnost služby. Deserializátor může být například nucen deserializovat hluboce vnořený objektový graf (objekt, který obsahuje jiný objekt, který obsahuje další objekt atd.) příchozí zprávou. DataContractSerializerXmlSerializer Metody volání vnořeným způsobem deserializace těchto grafů. Hluboké vnoření volání metody může vést k neopravitelnému StackOverflowException. Tato hrozba se zmírní nastavením MaxDepth kvóty pro omezení úrovně vnoření XML, jak je popsáno v části Používání XML Sejf ly dále v tématu.

Nastavení dalších kvót MaxReceivedMessageSize je zvlášť důležité při použití binárního kódování XML. Použití binárního kódování je poněkud ekvivalentní kompresi: malá skupina bajtů v příchozí zprávě může představovat velké množství dat. Proto i zpráva, která se hodí k limitu MaxReceivedMessageSize , může trvat mnohem více paměti v plně rozšířené podobě. Pokud chcete takové hrozby specifické pro XML zmírnit, je nutné správně nastavit všechny kvóty čtečky XML, jak je popsáno v části Používání XML Sejf ly dále v tomto tématu.

Omezení spotřeby paměti pomocí streamování

Při streamování můžete použít malé MaxReceivedMessageSize nastavení k ochraně před útoky na dostupnost služby. U streamování ale můžou být složitější scénáře. Služba pro nahrání souborů například přijímá soubory větší než všechny dostupné paměti. V tomto případě nastavte MaxReceivedMessageSize na extrémně velkou hodnotu, která očekává, že téměř žádná data se neukládá do vyrovnávací paměti a streamy zpráv přímo na disk. Pokud škodlivá zpráva může nějak vynutit WCF ukládat data do vyrovnávací paměti místo jeho streamování v tomto případě, MaxReceivedMessageSize už nebude chránit před zprávou, která přistupuje ke všem dostupným paměti.

Pro zmírnění této hrozby existují konkrétní nastavení kvóty pro různé komponenty zpracování dat WCF, které omezují ukládání do vyrovnávací paměti. Nejdůležitější z nich je MaxBufferSize vlastnost pro různé prvky přenosové vazby a standardní vazby. Při streamování by se tato kvóta měla nastavit s ohledem na maximální velikost paměti, kterou jste ochotni přidělit na zprávu. MaxReceivedMessageSizeStejně jako v případě , nastavení neukládá absolutní maximum pro spotřebu paměti, ale omezuje ho pouze na v rámci konstantního faktoru. Stejně jako v MaxReceivedMessageSizepřípadě , mějte na paměti, že je možné zpracovávat více zpráv současně.

MaxBufferSize Details

Tato MaxBufferSize vlastnost omezuje všechny hromadné ukládání WCF do vyrovnávací paměti. WCF například vždy uloží hlavičky SOAP do vyrovnávací paměti a chyby SOAP, stejně jako všechny části MIME, které nejsou v přirozeném pořadí čtení ve zprávě MTOM (Message Transmission Optimization Mechanism). Toto nastavení omezuje množství ukládání do vyrovnávací paměti ve všech těchto případech.

WCF toho dosahuje předáním MaxBufferSize hodnoty různým komponentám, které mohou ukládat do vyrovnávací paměti. Například některá CreateMessage přetížení Message třídy přebírají maxSizeOfHeaders parametr. WCF předá MaxBufferSize hodnotu tomuto parametru, aby omezila velikost vyrovnávací paměti hlavičky SOAP. Při použití Message třídy je důležité nastavit tento parametr přímo. Obecně platí, že při použití komponenty ve WCF, který přebírá parametry kvóty, je důležité pochopit důsledky zabezpečení těchto parametrů a správně je nastavit.

Kodér zpráv MTOM má MaxBufferSize také nastavení. Při použití standardních vazeb se nastaví automaticky na hodnotu na úrovni MaxBufferSize přenosu. Při použití elementu vazby kodéru zpráv MTOM k vytvoření vlastní vazby je však důležité nastavit MaxBufferSize vlastnost na bezpečnou hodnotu při použití streamování.

Útoky na streamování založené na XML

MaxBufferSize Samotné není dostatečné, aby se zajistilo, že WCF nelze při očekávaném streamování vynutit ukládání do vyrovnávací paměti. Například čtečky WCF XML vždy ukládat do vyrovnávací paměti celou počáteční značku elementu XML při zahájení čtení nového elementu. To se provádí tak, aby obory názvů a atributy byly správně zpracovány. Pokud MaxReceivedMessageSize je nakonfigurovaná tak, aby byla velká (například pro scénář streamování velkých souborů typu direct-to-disk), může být vytvořena škodlivá zpráva, kde celý text zprávy je velká počáteční značka elementu XML. Pokus o přečtení má za následek .OutOfMemoryException Toto je jedna z mnoha možných útoků založených na odepření služeb založených na JAZYCE XML, které je možné zmírnit pomocí kvót čtečky XML, popsané v části Používání XML Sejf ly dále v tomto tématu. Při streamování je obzvláště důležité nastavit všechny tyto kvóty.

Kombinování programovacích modelů streamování a ukládání do vyrovnávací paměti

Mnoho možných útoků vzniká z kombinování programovacích modelů streamování a nestreamovaných programovacích modelů ve stejné službě. Předpokládejme, že existuje kontrakt služby se dvěma operacemi: jeden přebírá Stream a druhý přebírá pole určitého vlastního typu. Předpokládejme také, že je nastavená na velkou hodnotu, MaxReceivedMessageSize aby první operace mohla zpracovávat velké datové proudy. Bohužel to znamená, že velké zprávy se teď dají odeslat i do druhé operace a deserializátor uloží data do paměti jako pole před zavolání operace. Jedná se o potenciální útok na dostupnost služby: MaxBufferSize kvóta neomezuje velikost textu zprávy, což je to, s čím deserializátor pracuje.

Z tohoto důvodu se vyhněte kombinování operací založených na datových proudech a nestreamovaných operací ve stejném kontraktu. Pokud musíte tyto dva programovací modely naprosto kombinovat, postupujte následovně:

  • Funkci vypněte IExtensibleDataObject nastavením IgnoreExtensionDataObject vlastnosti ServiceBehaviorAttribute na truehodnotu . Tím se zajistí, že se deserializují pouze členové, kteří jsou součástí smlouvy.

  • MaxItemsInObjectGraph Nastavte vlastnost DataContractSerializer na bezpečnou hodnotu. Tato kvóta je také k dispozici pro ServiceBehaviorAttribute atribut nebo prostřednictvím konfigurace. Tato kvóta omezuje počet objektů, které jsou deserializovány v jedné deserializační epizodě. Za normálních okolností se každý parametr operace nebo část textu zprávy v kontraktu zprávy deserializuje v jedné epizodě. Při deserializaci polí se každá položka pole počítá jako samostatný objekt.

  • Nastavte všechny kvóty čtečky XML na bezpečné hodnoty. Věnujte pozornost MaxDepth, MaxStringContentLengtha MaxArrayLength vyhněte se řetězcům v nestreamovaných operacích.

  • Projděte si seznam známých typů a mějte na paměti, že některé z nich je možné kdykoli vytvořit instanci (viz část "Zabránění načtení nezamýšlených typů" dále v tomto tématu).

  • Nepoužívejte žádné typy, které implementují IXmlSerializable rozhraní, které do vyrovnávací paměti velké množství dat. Nepřidávejte takové typy do seznamu známých typů.

  • Nepoužívejte XmlElementpole XmlNode , Byte pole nebo typy, které implementují ISerializable v kontraktu.

  • Nepoužívejte XmlElementpole XmlNode , Byte pole nebo typy, které se implementují ISerializable v seznamu známých typů.

Předchozí opatření se použijí, pokud nestreamovaná operace používá DataContractSerializer. Pokud používáte XmlSerializerprogramovací modely streamování a nestreamových proudů, nikdy nekombinujte ve stejné službě, protože nemá ochranu MaxItemsInObjectGraph kvóty.

Pomalé útoky streamu

Třída útoků dosílaných dosílání služby nezahrnuje spotřebu paměti. Místo toho útok zahrnuje pomalého odesílatele nebo příjemce dat. Při čekání na odeslání nebo přijetí dat se vyčerpá prostředky, jako jsou vlákna a dostupná připojení. K této situaci může dojít buď v důsledku škodlivého útoku, nebo z legitimního odesílatele nebo příjemce v pomalém síťovém připojení.

Pokud chcete tyto útoky zmírnit, nastavte správný časový limit přenosu. Další informace naleznete v tématu Kvóty přenosu. Za druhé, nikdy nepoužívejte synchronní Read nebo Write operace při práci s datovými proudy ve WCF.

Použití xml Sejf ly

Poznámka:

I když se tato část týká XML, informace platí také pro dokumenty JSON (JavaScript Object Notation). Kvóty fungují podobně pomocí mapování mezi JSON a XML.

Zabezpečené čtečky XML

Informační sada XML tvoří základ veškerého zpracování zpráv ve WCF. Při přijímání dat XML z nedůvěryhodného zdroje existuje řada možností útoku na dostupnost služby, které je potřeba zmírnit. WCF poskytuje speciální a zabezpečené čtečky XML. Tyto čtečky se vytvářejí automaticky při použití jednoho ze standardních kódování ve WCF (text, binární soubor nebo MTOM).

Některé funkce zabezpečení těchto čtenářů jsou vždy aktivní. Čtenáři například nikdy nezpracují definice typu dokumentu (DTD), které jsou potenciálním zdrojem útoků na dostupnost služby a nikdy by se neměly zobrazovat v legitimních zprávách SOAP. Mezi další funkce zabezpečení patří kvóty pro čtení, které je potřeba nakonfigurovat, které jsou popsány v následující části.

Při práci přímo se čtečkami XML (například při psaní vlastního kodéru nebo při přímé práci s Message třídou) vždy používejte zabezpečené čtečky WCF, pokud existuje možnost pracovat s nedůvěryhodnými daty. Vytvořte zabezpečené čtenáře voláním jedné ze statických metod objektu CreateTextReaderpro vytváření přetížení , CreateBinaryReadernebo CreateMtomReader třídy XmlDictionaryReader . Při vytváření čtečky předejte hodnoty zabezpečené kvóty. Nevolejte Create přetížení metody. Ty nevytvoří čtečku WCF. Místo toho se vytvoří čtenář, který není chráněný funkcemi zabezpečení popsanými v této části.

Kvóty čtečky

Zabezpečené čtečky XML mají pět konfigurovatelných kvót. Obvykle se konfigurují pomocí ReaderQuotas vlastnosti u elementů vazby kódování nebo standardních vazeb nebo pomocí objektu XmlDictionaryReaderQuotas předaného při vytváření čtečky.

MaxBytesPerRead

Tato kvóta omezuje počet bajtů, které se čtou v jedné Read operaci při čtení počáteční značky elementu a jeho atributů. (V jiných než streamovaných případech se samotný název elementu nezapočítá do kvóty.) MaxBytesPerRead je důležité z následujících důvodů:

  • Název elementu a jeho atributy se při čtení vždy ukládají do vyrovnávací paměti. Proto je důležité tuto kvótu správně nastavit v režimu streamování, aby se zabránilo nadměrnému ukládání do vyrovnávací paměti při očekávaném streamování. Informace o skutečném množství vyrovnávací paměti, které probíhá, najdete v MaxDepth části kvót.

  • Příliš mnoho atributů XML může využívat nepřiměřenou dobu zpracování, protože názvy atributů je nutné zkontrolovat jedinečnost. MaxBytesPerRead snižuje tuto hrozbu.

MaxDepth

Tato kvóta omezuje maximální hloubku vnoření elementů XML. Například dokument "<A><B><C/><B></A>" má vnořenou hloubku tří. MaxDepth je důležité z následujících důvodů:

  • MaxDepth komunikuje s MaxBytesPerRead: čtenář vždy uchovává data v paměti pro aktuální prvek a všechny jeho nadřazené prvky, takže maximální spotřeba paměti čtenáře je úměrná součinu těchto dvou nastavení.

  • Při deserializaci hluboko vnořeného objektového grafu je deserializátor nucen přistupovat k celému zásobníku a vyvolat neopravitelný StackOverflowException. Přímá korelace existuje mezi vnořením XML a vnořením objektů pro objekt i DataContractSerializerXmlSerializerpro . Slouží MaxDepth ke zmírnění této hrozby.

MaxNameTableCharCount

Tato kvóta omezuje velikost názvové tabulky čtenáře. Názvová tabulka obsahuje určité řetězce (například obory názvů a předpony), ke kterým dochází při zpracování dokumentu XML. Vzhledem k tomu, že jsou tyto řetězce uloženy do vyrovnávací paměti, nastavte tuto kvótu, aby se zabránilo nadměrnému ukládání do vyrovnávací paměti při očekávaném streamování.

MaxStringContentLength

Tato kvóta omezuje maximální velikost řetězce, kterou vrátí čtečka XML. Tato kvóta neomezuje spotřebu paměti v samotné čtečce XML, ale v komponentě, která používá čtečku. Pokud například DataContractSerializer používá čtečku zabezpečenou MaxStringContentLengthpomocí , ne deserializuje řetězce větší než tato kvóta. Při použití XmlDictionaryReader třídy přímo, ne všechny metody respektují tuto kvótu, ale pouze metody, které jsou speciálně navrženy pro čtení řetězců, jako je například ReadContentAsString metoda. Tato kvóta Value nemá vliv na vlastnost čtenáře, a proto by neměla být použita, pokud je nutná ochrana, kterou tato kvóta poskytuje.

MaxArrayLength

Tato kvóta omezuje maximální velikost pole primitiv, které vrátí čtečka XML, včetně bajtových polí. Tato kvóta neomezuje spotřebu paměti v samotné čtečce XML, ale v jakékoli komponentě, která používá čtečku. Pokud například používá čtečku DataContractSerializer zabezpečenou MaxArrayLengthpomocí , nezkonstruuje pole bajtů větší než tato kvóta. Při pokusu o kombinování programovacích modelů streamování a programovacích modelů ve vyrovnávací paměti v jednom kontraktu je důležité tuto kvótu nastavit. Mějte na paměti, že při použití XmlDictionaryReader třídy přímo, pouze metody, které jsou speciálně navrženy pro čtení pole libovolné velikosti určitých primitivních typů, například ReadInt32Array, respektují tuto kvótu.

Hrozby specifické pro binární kódování

Binární kódování XML WCF podporuje funkce slovníkových řetězců. Velký řetězec může být kódován pouze pomocí několika bajtů. To umožňuje významné zvýšení výkonu, ale přináší nové hrozby pro odepření služeb, které je potřeba zmírnit.

Existují dva druhy slovníků: statické a dynamické. Statický slovník je integrovaný seznam dlouhých řetězců, které mohou být reprezentovány pomocí krátkého kódu v binárním kódování. Tento seznam řetězců je opraven při vytváření čtečky a nelze ho změnit. Žádný z řetězců ve statickém slovníku, který WCF ve výchozím nastavení používá, není dostatečně velký, aby představoval závažnou hrozbu pro odepření služby, i když se můžou stále používat v útoku na rozšíření slovníku. Vpokročilých

Funkce dynamických slovníků umožňuje zprávám definovat vlastní řetězce a přidružit je ke krátkým kódům. Tato mapování řetězců na kód jsou uložena v paměti během celé komunikační relace, takže následné zprávy nemusí znovu odeslat řetězce a mohou využívat kódy, které jsou již definovány. Tyto řetězce mohou mít libovolnou délku, a proto představují vážnější hrozbu než řetězce ve statickém slovníku.

První hrozbou, kterou je potřeba zmírnit, je možnost, že se dynamický slovník (tabulka mapování řetězců na kód) stává příliš velkým. Tento slovník se může rozšířit v průběhu několika zpráv, takže kvóta MaxReceivedMessageSize nenabízí žádnou ochranu, protože se vztahuje pouze na každou zprávu samostatně. Proto existuje samostatná MaxSessionSize vlastnost, BinaryMessageEncodingBindingElement která omezuje velikost slovníku.

Na rozdíl od většiny ostatních kvót se tato kvóta vztahuje také při psaní zpráv. Pokud se při čtení zprávy překročí, je vyvolán obvyklým QuotaExceededException způsobem. Pokud se při zápisu zprávy překročí, všechny řetězce, které způsobují překročení kvóty, se zapíšou tak, jak jsou, bez použití funkce dynamických slovníků.

Rozšiřovací hrozby slovníku

Z rozšíření slovníku vzniká významná třída útoků specifických pro binární soubory. Malá zpráva v binární podobě se může převést na velmi velkou zprávu v plně rozšířené textové podobě, pokud využívá rozsáhlou funkci řetězcových slovníků. Rozšiřující faktor pro řetězce dynamického slovníku je omezen kvótou MaxSessionSize , protože žádný řetězec dynamického slovníku nepřekračuje maximální velikost celého slovníku.

Hodnota MaxNameTableCharCount, MaxStringContentLengtha MaxArrayLength vlastnosti omezují pouze spotřebu paměti. Obvykle se nevyžadují ke zmírnění jakýchkoli hrozeb v nestreamovém využití, protože využití paměti je již omezené MaxReceivedMessageSize. MaxReceivedMessageSize Počítá však bajty před rozšířením. Při použití binárního kódování by spotřeba paměti mohla potenciálně překročit MaxReceivedMessageSize, omezen pouze faktorem MaxSessionSize. Z tohoto důvodu je důležité při použití binárního kódování vždy nastavit všechny kvóty čtenáře (zejména MaxStringContentLength).

Při použití binárního kódování společně s DataContractSerializerIExtensibleDataObject rozhraním může být zneužito připojení slovníkového rozšiřujícího útoku. Toto rozhraní v podstatě poskytuje neomezené úložiště pro libovolná data, která nejsou součástí kontraktu. Pokud kvóty nelze nastavit dostatečně málo tak, aby MaxSessionSize násobení MaxReceivedMessageSize nenastavilo problém, zakažte IExtensibleDataObject funkci při použití binárního kódování. IgnoreExtensionDataObject Nastavte vlastnost na ServiceBehaviorAttribute atributtrue. Alternativně neimplementujte IExtensibleDataObject rozhraní. Další informace najdete v tématu Kontrakty dat kompatibilní s předáváním.

Souhrn kvót

Následující tabulka shrnuje pokyny k kvótám.

Podmínka Důležité kvóty k nastavení
Žádné streamování nebo streamování malých zpráv, textu nebo kódování MTOM MaxReceivedMessageSize, MaxBytesPerReada MaxDepth
Žádné streamování nebo streamování malých zpráv, binární kódování MaxReceivedMessageSize, MaxSessionSizea vše ReaderQuotas
Streamování velkých zpráv, textu nebo kódování MTOM MaxBufferSize a vše ReaderQuotas
Streamování velkých zpráv, binární kódování MaxBufferSize, MaxSessionSizea vše ReaderQuotas
  • Vypršení časového limitu na úrovni přenosu musí být vždy nastaveno a nikdy při použití synchronního čtení a zápisu nepoužívejte synchronní čtení a zápisy bez ohledu na to, jestli streamujete velké nebo malé zprávy.

  • Pokud pochybuje o kvótě, nastavte ji na bezpečnou hodnotu a neopustíte ji otevřenou.

Zabránění spuštění škodlivého kódu

Následující obecné třídy hrozeb mohou spouštět kód a mít nezamýšlené účinky:

  • Deserializátor načte škodlivý, nebezpečný nebo typ citlivý na zabezpečení.

  • Příchozí zpráva způsobí, že deserializátor vytvoří instanci normálně bezpečného typu takovým způsobem, že má nezamýšlené důsledky.

V následujících částech jsou tyto třídy hrozeb podrobněji popsány.

DataContractSerializer

(Informace o zabezpečení najdete XmlSerializerv příslušné dokumentaci.) Model zabezpečení je XmlSerializer podobný DataContractSerializermodelu zabezpečení , který se liší většinou v podrobnostech. Například XmlIncludeAttribute atribut se používá pro zahrnutí typu místo atributu KnownTypeAttribute . Některé hrozby, které jsou jedinečné pro toto XmlSerializer téma, jsou však popsány dále v tomto tématu.

Zabránění načtení nezamýšlených typů

Načítání nezamýšlených typů může mít významné důsledky, ať už je typ škodlivý nebo má pouze vedlejší účinky citlivé na zabezpečení. Typ může obsahovat zneužitelné ohrožení zabezpečení, provádět akce citlivé na zabezpečení v konstruktoru nebo konstruktoru třídy, mít velké nároky na paměť, které usnadňují útoky na dostupnost služby nebo můžou vyvolat neobnovitelné výjimky. Typy můžou mít konstruktory tříd, které se spouštějí, jakmile je typ načten a před vytvořením všech instancí. Z těchto důvodů je důležité řídit sadu typů, které může deserializátor načíst.

Deserializuje DataContractSerializer volně propojeným způsobem. Nikdy nečte z příchozích dat názvy typů a sestavení modulu CLR (Common Language Runtime). To je podobné chování XmlSerializer, ale liší se od chování NetDataContractSerializer, BinaryFormattera SoapFormatter. Volné spojení představuje stupeň bezpečnosti, protože vzdálený útočník nemůže načíst libovolný typ pouhým pojmenováním tohoto typu ve zprávě.

Vždy DataContractSerializer je povoleno načíst typ, který se aktuálně očekává podle kontraktu. Pokud má například datový kontrakt datový člen typu Customer, DataContractSerializer je povoleno načíst Customer typ při deserializaci tohoto datového členu.

Kromě toho podporuje DataContractSerializer polymorfismus. Datový člen může být deklarován jako Object, ale příchozí data mohou obsahovat Customer instanci. To je možné pouze v případě, že Customer byl typ "známý" deserializátoru prostřednictvím jednoho z těchto mechanismů:

  • KnownTypeAttribute atribut použitý u typu.

  • KnownTypeAttribute atribut určující metodu, která vrací seznam typů.

  • Atribut ServiceKnownTypeAttribute.

  • Oddíl KnownTypes konfigurace.

  • Seznam známých typů explicitně předán DataContractSerializer během výstavby, pokud používá serializátor přímo.

Každý z těchto mechanismů zvyšuje povrchovou plochu tím, že zavádí více typů, které deserializátor může načíst. Kontrolujte každý z těchto mechanismů, abyste zajistili, že do seznamu známých typů nebudou přidány žádné škodlivé nebo nezamýšlené typy.

Jakmile je známý typ v oboru, lze ho kdykoli načíst a instance typu lze vytvořit, i když kontrakt zakáže jeho skutečné použití. Předpokládejme například, že typ "MyDangerousType" je přidán do seznamu známých typů pomocí jednoho z výše uvedených mechanismů. To znamená, že:

  • MyDangerousType je načten a jeho konstruktor třídy běží.

  • I když deserializujete kontrakt dat s řetězcovým datovým členem, může škodlivá zpráva způsobit vytvoření instance MyDangerousType . Kód v MyDangerousTypeobjektu , například vlastnosti setters, může běžet. Po dokončení se deserializátor pokusí přiřadit tuto instanci datovému členu řetězce a selže s výjimkou.

Při zápisu metody, která vrací seznam známých typů nebo při předávání seznamu přímo DataContractSerializer konstruktoru, ujistěte se, že kód, který seznam připraví, je zabezpečený a pracuje pouze s důvěryhodnými daty.

Pokud v konfiguraci zadáte známé typy, ujistěte se, že je konfigurační soubor zabezpečený. Vždy používejte silné názvy v konfiguraci (zadáním veřejného klíče podepsaného sestavení, kde se typ nachází), ale nezadávejte verzi typu, která se má načíst. Pokud je to možné, zavaděč typů automaticky vybere nejnovější verzi. Pokud v konfiguraci zadáte konkrétní verzi, spustíte následující riziko: Typ může mít chybu zabezpečení, která může být opravena v budoucí verzi, ale zranitelná verze se stále načte, protože je explicitně určená v konfiguraci.

Příliš mnoho známých typů má jiný následek: Vytvoří DataContractSerializer mezipaměť serializace/deserializační kód v doméně aplikace s položkou pro každý typ, který musí serializovat a deserializovat. Tato mezipaměť se nikdy nevymazá, pokud je doména aplikace spuštěná. Útočník, který si je vědom toho, že aplikace používá mnoho známých typů může způsobit deserializaci všech těchto typů, což způsobí, že mezipaměť spotřebuje nepřiměřeně velké množství paměti.

Zabránění tomu, aby typy byly v nezamýšleném stavu

Typ může mít interní omezení konzistence, která se musí vynutit. Je třeba dbát na to, abyste se vyhnuli narušení těchto omezení během deserializace.

Následující příklad typu představuje stav vzduchového zámku na vesmírné lodi a vynucuje omezení, že vnitřní i vnější dveře nelze otevřít současně.

[DataContract]
public class SpaceStationAirlock
{
    [DataMember]
    private bool innerDoorOpenValue = false;
    [DataMember]
    private bool outerDoorOpenValue = false;

    public bool InnerDoorOpen
    {
        get { return innerDoorOpenValue; }
        set
        {
            if (value & outerDoorOpenValue)
                throw new Exception("Cannot open both doors!");
            else innerDoorOpenValue = value;
        }
    }
    public bool OuterDoorOpen
    {
        get { return outerDoorOpenValue; }
        set
        {
            if (value & innerDoorOpenValue)
                throw new Exception("Cannot open both doors!");
            else outerDoorOpenValue = value;
        }
    }
}
<DataContract()> _
Public Class SpaceStationAirlock
    <DataMember()> Private innerDoorOpenValue As Boolean = False
    <DataMember()> Private outerDoorOpenValue As Boolean = False

    Public Property InnerDoorOpen() As Boolean
        Get

            Return innerDoorOpenValue
        End Get
        Set(ByVal value As Boolean)
            If (value & outerDoorOpenValue) Then
                Throw New Exception("Cannot open both doors!")
            Else
                innerDoorOpenValue = value
            End If
        End Set
    End Property

    Public Property OuterDoorOpen() As Boolean
        Get
            Return outerDoorOpenValue
        End Get
        Set(ByVal value As Boolean)
            If (value & innerDoorOpenValue) Then
                Throw New Exception("Cannot open both doors!")
            Else
                outerDoorOpenValue = value
            End If
        End Set
    End Property
End Class

Útočník může takhle poslat škodlivou zprávu, obejít omezení a dostat objekt do neplatného stavu, což může mít nezamýšlené a nepředvídatelné důsledky.

<SpaceStationAirlock>
    <innerDoorOpen>true</innerDoorOpen>
    <outerDoorOpen>true</outerDoorOpen>
</SpaceStationAirlock>

Této situaci se můžete vyhnout tím, že si uvědomíte následující body:

  • DataContractSerializer Když deserializuje většinu tříd, konstruktory se nespustí. Proto nespoléhejte na žádnou správu stavu provedenou v konstruktoru.

  • Pomocí zpětných volání se ujistěte, že je objekt v platném stavu. Zpětné volání označené atributem OnDeserializedAttribute je zvlášť užitečné, protože se spustí po dokončení deserializace a má šanci prozkoumat a opravit celkový stav. Další informace naleznete v tématu Zpětná volání serializace odolné proti verzi.

  • Nevytáhejte typy kontraktů dat tak, aby se spoléhaly na žádné konkrétní pořadí, ve kterém se musí volat settery vlastností.

  • Dbejte na to, aby se používaly starší typy označené atributem SerializableAttribute . Mnohé z nich byly navrženy tak, aby fungovaly se vzdálené komunikace rozhraní .NET Framework pouze pro použití s důvěryhodnými daty. Existující typy označené tímto atributem nemusí být navrženy s ohledem na zabezpečení stavu.

  • Nespoléhejte na IsRequired vlastnost atributu DataMemberAttribute k zajištění přítomnosti dat, pokud jde o bezpečnost státu. Data můžou být nullvždy , zeronebo invalid.

  • Nikdy nedůvěřujte deserializaci objektového grafu z nedůvěryhodného zdroje dat bez jeho ověření jako první. Každý jednotlivý objekt může být v konzistentním stavu, ale graf objektů jako celek nemusí být. I když je režim zachování grafu objektu zakázán, může deserializovaný graf mít více odkazů na stejný objekt nebo mít cyklické odkazy. Další informace naleznete v tématu Serializace a deserializace.

Bezpečné použití NetDataContractSerializer

Jedná se NetDataContractSerializer o serializační modul, který používá úzkou spojku k typům. To je podobné jako a BinaryFormatterSoapFormatter. To znamená, že určuje, který typ má vytvořit instanci načtením sestavení rozhraní .NET Framework a názvu typu z příchozích dat. Ačkoli je součástí WCF, neexistuje žádný způsob zapojení do tohoto serializačního modulu; Vlastní kód musí být napsán. Poskytuje se NetDataContractSerializer především k usnadnění migrace z vzdálené komunikace rozhraní .NET Framework na WCF. Další informace naleznete v příslušné části serializace a deserializace.

Protože samotná zpráva může znamenat, že lze načíst libovolný typ, NetDataContractSerializer mechanismus je ze své podstaty nezabezpečený a měl by se používat pouze s důvěryhodnými daty. Další informace naleznete v průvodci zabezpečením BinaryFormatter.

I když se používají s důvěryhodnými daty, příchozí data mohou nedostatečně určit typ, který se má načíst, zejména pokud AssemblyFormat je vlastnost nastavena na Simple. Každý, kdo má přístup k adresáři aplikace nebo globální mezipaměti sestavení, může místo toho, který má načíst, nahradit škodlivý typ. Vždy zajistěte zabezpečení adresáře vaší aplikace a globální mezipaměti sestavení tím, že správně nastavíte oprávnění.

Obecně platí, že pokud povolíte částečně důvěryhodný přístup kódu k vaší NetDataContractSerializer instanci nebo jinak řídíte selektorISurrogateSelector náhradních () nebo pořadač serializace (SerializationBinder), může kód provádět velkou kontrolu nad serializací a deserializací procesu. Může například vložit libovolné typy, vést k vyzrazení informací, manipulovat s výsledným grafem objektu nebo serializovanými daty nebo přetékat výsledný serializovaný datový proud.

Dalším zájmem o zabezpečení je NetDataContractSerializer odepření služby, nikoli hrozba spuštění škodlivého kódu. Při použití NetDataContractSerializervždy nastavte kvótu MaxItemsInObjectGraph na bezpečnou hodnotu. Je snadné vytvořit malou škodlivou zprávu, která přiděluje pole objektů, jejichž velikost je omezena pouze touto kvótou.

Hrozby specifické pro XmlSerializer

Model XmlSerializer zabezpečení je podobný DataContractSerializermodelu . Několik hrozeb, nicméně, jsou jedinečné pro XmlSerializer.

Generuje XmlSerializer sestavení serializace za běhu, které obsahují kód, který ve skutečnosti serializuje a deserializuje; tato sestavení jsou vytvořena v adresáři dočasných souborů. Pokud má nějaký jiný proces nebo uživatel přístupová práva k danému adresáři, může přepsat serializace/deserializační kód libovolným kódem. Potom XmlSerializer tento kód spustí pomocí kontextu zabezpečení místo serializace/deserializace kódu. Ujistěte se, že jsou oprávnění správně nastavená v adresáři dočasných souborů, aby k tomu nedocházelo.

XmlSerializer také režim, ve kterém používá předgenerovaná serializace sestavení namísto jejich generování za běhu. Tento režim se aktivuje vždy, když XmlSerializer najde vhodné sestavení serializace. Kontroluje XmlSerializer , zda bylo sestavení serializace podepsáno stejným klíčem, který byl použit k podepsání sestavení obsahující typy serializované. Tato možnost nabízí ochranu před škodlivými sestaveními, která jsou maskována jako sestavení serializace. Pokud však sestavení obsahující vaše serializovatelné typy není podepsáno, XmlSerializer nelze provést tuto kontrolu a použít jakékoli sestavení se správným názvem. To umožňuje spuštění škodlivého kódu. Vždy podepište sestavení, která obsahují vaše serializovatelné typy, nebo přísně řídit přístup k adresáři vaší aplikace a globální mezipaměti sestavení, aby se zabránilo zavedení škodlivých sestavení.

Může XmlSerializer se jednat o útok na dostupnost služby. Nemá XmlSerializer kvótu MaxItemsInObjectGraph (jak je k dispozici na této straně DataContractSerializer). Proto deserializuje libovolné množství objektů, omezené pouze velikostí zprávy.

Částečné hrozby důvěryhodnosti

Všimněte si následujících obav týkajících se hrozeb souvisejících s kódem spuštěným s částečnou důvěryhodností. Mezi tyto hrozby patří škodlivý částečně důvěryhodný kód a škodlivý částečně důvěryhodný kód v kombinaci s jinými scénáři útoku (například částečně důvěryhodný kód, který vytváří určitý řetězec a pak ho deserializuje).

  • Při použití jakýchkoli komponent serializace nikdy nevytvrzet žádná oprávnění před takovým použitím, a to ani v případě, že celý scénář serializace je v rozsahu vašeho kontrolního výrazu, a neřešíte žádné nedůvěryhodné data nebo objekty. Takové použití může vést k ohrožením zabezpečení.

  • V případech, kdy částečně důvěryhodný kód má kontrolu nad serializačním procesem, a to buď prostřednictvím bodů rozšiřitelnosti (náhradních dotazů), typů serializovaných nebo jinými prostředky, může částečně důvěryhodný kód způsobit, že serializátor vypíše velké množství dat do serializovaného datového proudu, což může způsobit odepření služby (DoS) příjemci tohoto datového proudu. Pokud serializujete data určená pro cíl, který je citlivý na hrozby DoS, serializujte částečně důvěryhodné typy nebo jinak nechejte serializaci částečně důvěryhodného kódu serializace.

  • Pokud povolíte částečně důvěryhodný přístup kódu k vaší DataContractSerializer instanci nebo jinak řídíte náhradní kontrakty dat, může provádět velkou kontrolu nad serializací/deserializačním procesem. Může například vložit libovolné typy, vést k vyzrazení informací, manipulovat s výsledným grafem objektu nebo serializovanými daty nebo přetékat výsledný serializovaný datový proud. NetDataContractSerializer Ekvivalentní hrozba je popsaná v části Použití NetDataContractSerializer Bezpečně.

  • DataContractAttribute Pokud se atribut použije na typ (nebo typ označený jakoSerializableAttribute, ale neníISerializable), deserializátor může vytvořit instanci takového typu, i když jsou všechny konstruktory neveřejné nebo chráněné požadavky.

  • Nikdy nedůvěřujte výsledku deserializace, pokud nejsou data, která mají být deserializována, důvěryhodná a jste si jisti, že všechny známé typy jsou typy, kterým důvěřujete. Všimněte si, že známé typy nejsou načteny z konfiguračního souboru aplikace (ale jsou načteny z konfiguračního souboru počítače) při spuštění v částečné důvěryhodnosti.

  • Pokud předáte DataContractSerializer instanci s náhradním kódem přidaným do částečně důvěryhodného kódu, může kód změnit všechna upravitelná nastavení pro tuto náhradní bránu.

  • U deserializovaného objektu, pokud čtečka XML (nebo data v ní) pochází z částečně důvěryhodného kódu, zachází s výsledným deserializovaným objektem jako nedůvěryhodnými daty.

  • Skutečnost, že typ nemá žádné veřejné členy, neznamená, ExtensionDataObject že data v něm jsou zabezpečená. Pokud například deserializujete z privilegovaného zdroje dat do objektu, ve kterém se některá data nacházejí, pak tento objekt předáte částečně důvěryhodnému kódu, může částečně důvěryhodný kód číst data v objektu ExtensionDataObject serializací objektu. Zvažte nastavení IgnoreExtensionDataObjecttrue při deserializaci z privilegovaného zdroje dat do objektu, který se později předá částečně důvěryhodnému kódu.

  • DataContractSerializer a DataContractJsonSerializer podporuje serializaci soukromých, chráněných, interních a veřejných členů v plné důvěryhodnosti. V částečném vztahu důvěryhodnosti však lze serializovat pouze veřejné členy. Vyvolá SecurityException se, pokud se aplikace pokusí serializovat nepřístupný člen.

    Chcete-li povolit serializaci interních nebo chráněných vnitřních členů v částečné důvěryhodnosti, použijte InternalsVisibleToAttribute atribut sestavení. Tento atribut umožňuje sestavení deklarovat, že jeho vnitřní členy jsou viditelné pro některé jiné sestavení. V tomto případě sestavení, které chce mít své vnitřní členy serializované deklaruje, že jeho interní členy jsou viditelné pro System.Runtime.Serialization.dll.

    Výhodou tohoto přístupu je, že nevyžaduje cestu generování kódu se zvýšenými oprávněními.

    Současně existují dvě hlavní nevýhody.

    První nevýhodou je, že opt-in vlastnost InternalsVisibleToAttribute atributu je assembly-wide. To znamená, že nelze určit, že pouze určitá třída může mít své interní členy serializován. Samozřejmě, můžete se stále rozhodnout, že serializovat konkrétní interní člen, jednoduše nepřidá DataMemberAttribute atribut tohoto člena. Podobně se vývojář může rozhodnout, že člen bude interně interní než soukromý nebo chráněný, s mírnými obavami z viditelnosti.

    Druhou nevýhodou je, že stále nepodporuje soukromé ani chráněné členy.

    Pokud chcete ilustrovat použití atributu InternalsVisibleToAttribute v částečné důvěryhodnosti, zvažte následující program:

        public class Program
        {
            public static void Main(string[] args)
            {
                try
                {
    //              PermissionsHelper.InternetZone corresponds to the PermissionSet for partial trust.
    //              PermissionsHelper.InternetZone.PermitOnly();
                    MemoryStream memoryStream = new MemoryStream();
                    new DataContractSerializer(typeof(DataNode)).
                        WriteObject(memoryStream, new DataNode());
                }
                finally
                {
                    CodeAccessPermission.RevertPermitOnly();
                }
            }
    
            [DataContract]
            public class DataNode
            {
                [DataMember]
                internal string Value = "Default";
            }
        }
    

    V příkladu výše PermissionsHelper.InternetZone odpovídá PermissionSet částečnému vztahu důvěryhodnosti. Bez atributu InternalsVisibleToAttribute se aplikace nezdaří a vyvolá SecurityException indikující, že neveřejné členy nelze serializovat v částečném vztahu důvěryhodnosti.

    Pokud však do zdrojového souboru přidáme následující řádek, program se úspěšně spustí.

    [assembly:System.Runtime.CompilerServices.InternalsVisibleTo("System.Runtime.Serialization, PublicKey = 00000000000000000400000000000000")]
    

Další obavy týkající se správy stavů

Za zmínku stojí několik dalších problémů týkajících se správy stavu objektů:

  • Při použití programovacího modelu založeného na streamu s přenosem streamování dojde ke zpracování zprávy při doručení zprávy. Odesílatel zprávy může přerušit operaci odeslání uprostřed datového proudu a nechat kód nepředvídatelným stavem, pokud by byl očekáváno více obsahu. Obecně se nespoléhejte na dokončení datového proudu a neprovádějte žádnou práci v operaci založené na datovém proudu, která se nedá vrátit zpět v případě přerušení datového proudu. To platí také pro situaci, kdy může být zpráva po textu streamování poškozena (například může chybět koncová značka obálky SOAP nebo může obsahovat druhý text zprávy).

  • IExtensibleDataObject Použití této funkce může způsobit vygenerování citlivých dat. Pokud přijímáte data z nedůvěryhodného zdroje do kontraktů dat a IExtensibleObjectData později je znovu vygenerujete v zabezpečeném kanálu, kde jsou zprávy podepsány, můžete potenciálně získat data, o kterých nic nevíte. Celkový stav, který odesíláte, může být navíc neplatný, pokud vezmete v úvahu známé i neznámé části dat. Vyhýbejte se této situaci tak, že buď selektivně nastavíte vlastnost dat rozšíření, null nebo selektivně zakážete IExtensibleObjectData funkci.

Import schématu

Obvykle se proces importu schématu pro generování typů děje pouze v době návrhu, například při použití nástroje ServiceModel Metadata Utility (Svcutil.exe) ve webové službě k vygenerování klientské třídy. V pokročilejších scénářích však můžete zpracovat schéma za běhu. Mějte na paměti, že tímto způsobem můžete vystavit rizika odepření služeb. Import některých schématu může trvat delší dobu. Pokud schémata pravděpodobně pocházejí z nedůvěryhodného zdroje, nikdy v takových scénářích nepoužívejte XmlSerializer komponentu importu schématu.

Hrozby specifické pro integraci ASP.NET AJAX

Když uživatel implementuje WebScriptEnablingBehavior nebo WebHttpBehaviorwcf zveřejňuje koncový bod, který může přijímat zprávy XML i JSON. Existuje však pouze jedna sada kvót pro čtení, kterou používá čtečka XML i čtečka JSON. Některá nastavení kvóty můžou být vhodná pro jednoho čtenáře, ale pro druhou je příliš velká.

Při implementaci WebScriptEnablingBehaviormá uživatel možnost zveřejnit v koncovém bodu javascriptový proxy server. Je třeba zvážit následující problémy se zabezpečením:

  • Informace o službě (názvy operací, názvy parametrů atd.) je možné získat prozkoumáním proxy javascriptového serveru.

  • Při použití koncového bodu JavaScriptu mohou být citlivé a soukromé informace zachovány v mezipaměti webového prohlížeče klienta.

Poznámka ke komponentám

WCF je flexibilní a přizpůsobitelný systém. Většina obsahu tohoto tématu se zaměřuje na nejběžnější scénáře použití WCF. Technologie WCF však může vytvářet komponenty mnoha různými způsoby. Je důležité porozumět dopadům na zabezpečení používání jednotlivých komponent. Zejména jde o toto:

  • Pokud musíte použít čtečky XML, použijte čtenáře XmlDictionaryReader třídy, které poskytuje, na rozdíl od jiných čtenářů. Sejf čtenáři se vytvářejí pomocí , CreateTextReaderCreateBinaryReadernebo CreateMtomReader metod. Nepoužívejte metodu Create . Vždy konfigurujte čtenáře se bezpečnými kvótami. Serializační moduly ve WCF jsou zabezpečené pouze při použití se zabezpečenými čtečkami XML z WCF.

  • Při použití DataContractSerializer k deserializaci potenciálně nedůvěryhodných dat vždy nastavte MaxItemsInObjectGraph vlastnost.

  • Při vytváření zprávy nastavte maxSizeOfHeaders parametr, pokud MaxReceivedMessageSize nenabízí dostatečnou ochranu.

  • Při vytváření kodéru vždy nakonfigurujte příslušné kvóty, například MaxSessionSize a MaxBufferSize.

  • Pokud používáte filtr zpráv XPath, nastavte NodeQuota omezení počtu uzlů XML, které filtr navštíví. Nepoužívejte výrazy XPath, které by mohly trvat dlouhou dobu, než se vypočítá, aniž byste museli navštívit mnoho uzlů.

  • Obecně platí, že pokud používáte libovolnou komponentu, která přijímá kvótu, seznamte se s důsledky zabezpečení a nastavte ji na bezpečnou hodnotu.

Viz také