în Unity 3.0, webplayer implementează un model de securitate foarte similar cu cel folosit de Adobe Flash Player-ul. Aceste restricții de securitate se aplică numai webplayer și editorului atunci când ținta de construire activă este WebPlayer. Modelul de securitate are mai multe părți:
- restricții privind accesarea datelor pe un alt domeniu decât cel care vă găzduiește .fișier unity3d.
- unele limitări privind utilizarea prizelor.
- interzicerea invocării oricărei metode pe care am considerat-o în afara limitelor. (lucruri ca fișier.Șterge, etc).
- interzicerea utilizării sistemului.Reflecție.* pentru a apela metode private/interne în clase pe care nu le-ați scris.
în prezent, doar primele două părți ale modelului de securitate sunt emulate în Editor.
funcționalitatea de rețea muti-player încorporată a Unity (UnityEngine.Network
, UnityEngine.NetworkView
clase etc) nu este afectată.
acest document descrie cum să vă asigurați că conținutul dvs. continuă să funcționeze cu versiunea 3.0 A Unity webplayer.
- consultați referința API Unity Pentru informații despre clasa WWW.
- consultați referința API.net pentru informații despre clasa Socket. net.
clasa WWW și sockets utilizează aceeași schemă de politici, dar în afară de aceasta sunt sisteme complet separate. Politica WWW definește doar permisiunile pentru serviciul web unde este găzduită politica, dar politicile socket se aplică tuturor conexiunilor socket TCP / UDP.
editorul Unity vine cu o caracteristică „Emulate Web Security”, care impune modelul de securitate webplayer.Acest lucru facilitează detectarea problemelor din confortul editorului. Puteți găsi această setare înedit->Setări proiect – > Editor. Consultați și setările editorului.
Unity webplayer se așteaptă ca un fișier de politică servit http numit crossdomain.xml
să fie disponibil pe domeniul pe care doriți să îl accesați cu clasa WWW(deși acest lucru nu este necesar dacă este același domeniu care găzduiește fișierul unity3d).
de exemplu, imaginați-vă un joc tetris, găzduit la următoarea adresă url:
http://gamecompany.com/games/tetris.unity3d
trebuie să acceseze o listă highscore de la următoarea adresă url:
http://highscoreprovider.net/gethighscore.php
în acest caz, va trebui să plasați un fișier crossdomain.xml
la rădăcina highscoreprovider.net domeniu ca acesta: http://highscoreprovider.net/crossdomain.xml
conținutul fișierului crossdomain.xml
este în formatul utilizat de Flash player. Este foarte probabil că veți găsigăsiți fișierul crossdomain.xml
deja în vigoare. Politica din fișier arată astfel:
<?xml version="1.0"?><cross-domain-policy><allow-access-from domain="*"/></cross-domain-policy>
când acest fișier este plasat la http://highscoreprovider.net/crossdomain.xml, proprietarul acelui domeniu declară acest lucruconținutul serverului web poate fi accesat de orice webplayer provenind din orice domeniu.
Unity webplayer nu acceptă etichetele < allow-http-request-headers-from domain>și < site-control allowed-cross-domain-policies>. Rețineți că crossdomain.xml
ar trebui să fie un fișier ASCII.
depanarea
setarea unei variabile de mediu ENABLE_CROSSDOMAIN_LOGGING
la 1
va determina generarea mesajelor consolei pe măsură ce Unity runtime preia și decodează fișierul crossdomain.xml
. Pe un Mac puteți seta variabile de mediu globale în /etc/launchd.conf
. Pe un PC utilizați panoul de Control- > sistem și securitate- > sistem – >Setări avansate de sistem – >variabile de mediu…
Iată un exemplu de ieșire cu acest set de variabile de mediu, atunci când webplayer încearcă să aducă o imagine de pe un server de la distanță:
Determining crossdomain.xml location for request: http://www.remoteserver.com/image.jpgAbout to parse url: http://www.remoteserver.com/image.jpgDetermining crossdomain.xml location for request: http://www.remoteserver.com/image.jpgAbout to parse url: http://www.remoteserver.com/crossdomain.xmlAbout to parse url: http://www.remoteserver.com/image.jpgDetermining crossdomain.xml location for request: http://www.remoteserver.com/image.jpgDownload had OK statuscodeReceived the following crossdomain.xml--------------------------------------<?xml version="1.0"?><cross-domain-policy><allow-access-from domain="*"/></cross-domain-policy>----------------------received policyParsing: cross-domain-policycross-domain-policyParsing: allow-access-fromallow-access-from domain: *done parsing policycrossdomain.xml was succesfully parsedAbout to parse url: http://www.remoteserver.com/image.jpgChecking if http://www.remoteserver.com/image.jpg is a valid domainChecking request-host: www.remoteserver.com against valid domain: *All requirements met, the request is approved
când rulați în Editor, aceste mesaje sunt scrise editorului.jurnal. Încercarea de a citi un fișier crossdomain.xml
stocat incorect ca utf16
cu un BOM
va duce la eșecul de a analiza xml:
BuildFlashPolicy caught an exception while parsing http://www.remoteserver.com/crossdomain.xml: Expected element
acest lucru se datorează faptului că BOM
nu este de așteptat. Utilizarea unui fișier utf16
neacceptat fără BOM
va avea ca rezultat:
BuildFlashPolicy caught an exception while parsing http://www.remoteserver.com/crossdomain.xml: Policy can't be constructed from empty stream.
acest lucru se datorează faptului că primul octet din fișier este zero, ceea ce face ca parserul să creadă că a ajuns la sfârșitul fișierului. Crossdomain.xml
trebuie să fie un fișier ASCII.
implicații pentru utilizarea soclurilor:
un Unity webplayer are nevoie de o politică de servire a soclului pentru a se conecta la o anumită gazdă. Această politică este în mod implicit găzduită de gazda țintă pe portul 843, dar poate fi găzduită și pe alte porturi. Diferența funcțională cu un port non-implicit este că acesta trebuie preluat manual cu securitate.PrefetchSocketPolicy () apel API și dacă este găzduit pe un port mai mare decât 1024 Politica poate oferi acces numai la alte porturi mai mari decât 1024.
când utilizați portul implicit funcționează astfel: un Unity webplayer încearcă să facă o conexiune TCP socket la o gazdă, verifică mai întâi că serverul gazdă va accepta connection.It face acest lucru prin deschiderea unui socket TCP pe portul 843, emite o solicitare și se așteaptă să primească o politică socket peste noua conexiune. Unity webplayer verifică apoi că Politica gazdei permite conectarea să continue și va continua fără eroare dacă da. Acest proces se întâmplă în mod transparent cu codul utilizatorului, care nu trebuie modificat pentru a utiliza acest model de securitate. Un exemplu de politică socket arată astfel:
<?xml version="1.0"?><cross-domain-policy> <allow-access-from domain="*" to-ports="1200-1220"/> </cross-domain-policy>"
această politică spune în mod eficient „conținutul din orice domeniu este liber să facă conexiuni socket la porturile 1200-1220”. Unity webplayer va respecta acest lucru, și rejectany încercat conexiune socket folosind un port în afara acestui interval (o SecurityException va fi aruncat).
atunci când se utilizează conexiuni UDP Politica poate fi, de asemenea, preluat automat atunci când au nevoie să fie puse în aplicare într-un mod similar cu TCP. Diferența este că preluarea automată cu TCP se întâmplă atunci când vă conectați la ceva (vă asigură că vi se permite să vă conectați la un server), dar cu UDP, deoarece este fără conexiune, se întâmplă și atunci când apelați orice punct API care trimite sau primește date (vă asigură că vi se permite să trimiteți/primiți trafic către/de la un server).
formatul utilizat pentru politica socket este același cu cel utilizat de Flash player, cu excepția faptului că unele etichete nu sunt acceptate. Unity webplayer acceptă doar ” * „ca valoare validă pentru setarea domeniului, iar setarea” to-ports ” este obligatorie.
<?xml version="1.0" encoding="ISO-8859-1"?><!ELEMENT cross-domain-policy (allow-access-from*)><!ELEMENT allow-access-from EMPTY><!ATTLIST allow-access-from domain CDATA #REQUIRED><!ATTLIST allow-access-from to-ports CDATA #REQUIRED>
Politica socket se aplică atât tipurilor de conexiuni TCP, cât și UDP, astfel încât traficul UDP și TCP să poată fi controlat de un singur server de politici.
pentru confortul dvs., oferim un mic program care ascultă pur și simplu la portul 843; atunci când pe o conexiune primește un șir de solicitare, acesta va răspunde cu o politică socket validă.Codul serverului poate fi găsit în folderul Unity install, în Data/Tools/SocketPolicyServer pe Windows sau /Unity.app / Contents/Tools / SocketPolicyServer pe OS X. rețineți că executabilul pre-construit poate fi rulat pe Mac, deoarece este un executabil Mono. Doar tastați ” mono sockpol.exe ” pentru ao rula. Rețineți că acest exemplu de cod arată comportamentul corect al unui server de politici socket. Mai exact, serverul se așteaptă să primească un șir terminat la zero care conține <policy-file-request/>. Trimite Clientului documentul XML de politică socket numai atunci când acest șir (și exact acest șir) a fost primit. Mai mult, este necesar ca antetul xml și corpul xml să fie trimise cu o singură scriere socket. Ruperea antetului și a corpului în operații separate de scriere a soclului poate provoca excepții de securitate din cauza unității care primește o politică incompletă. Dacă întâmpinați probleme cu propriul server, vă rugăm să luați în considerare utilizarea exemplului pe care îl oferim. Acest lucru ar trebui să vă ajute să diagnosticați dacă aveți probleme de server sau de rețea.
bibliotecile de rețele terțe, utilizate în mod obișnuit pentru rețelele de jocuri multiplayer, ar trebui să poată lucra cu aceste cerințe atâta timp cât nu depind de funcționalitatea peer 2 peer (vezi mai jos), ci utilizează servere dedicate. Acestea uneori chiar ies din cutie cu suport pentru politicile de găzduire.
notă: În timp ce fișierele de politică crossdomain.xml
și socket sunt ambele documente xml și sunt în general similare, modul în care aceste documente sunt servite sunt foarte diferite. Crossdomain.xml
(care se aplică cererilor http) este preluat folosind http pe portul 80, unde-ca politica socket este preluată din portul 843 folosind un server banal care implementează <policy-file-request/>. Nu puteți utiliza un server http pentru a emite fișierul de politică socket și nici nu puteți configura un server care trimite pur și simplu fișierul de politică socket ca răspuns la o conexiune socket pe portul 843. Rețineți, de asemenea, că fiecare server la care vă conectați necesită propriul server de politici socket.
Debugging
puteți utiliza telnet
pentru a vă conecta la serverul de politici socket. Un exemplu de sesiune este prezentat mai jos:
host$ telnet localhost 843Trying 127.0.0.1...Connected to localhost.Escape character is '^]'.<policy-file-request/><?xml version='1.0'?><cross-domain-policy> <allow-access-from domain="*" to-ports="*" /></cross-domain-policy>Connection closed by foreign host.host$
în această sesiune de exemplu, telnet este utilizat pentru a vă conecta la localhost pe portul 843. Telnet răspunde cu primele trei linii și apoi așteaptă ca utilizatorul să introducă ceva. Utilizatorul a introdus șirul de solicitare de politică<policy-file-request/ >, pe care serverul de politică socket îl primește și răspunde cu Politica socket. Serverul se deconectează apoi determinând telnet să raporteze că conexiunea a fost închisă.
prize de ascultare
nu puteți crea prize de ascultare în webplayer, acesta nu poate acționa ca un server. Prin urmare, webplayerii nu pot comunica direct între ei (peer 2 peer). Când utilizați prize TCP, vă puteți conecta numai la puncte finale la distanță, cu condiția să fie permisă prin sistemul de politici socket. Pentru UDP funcționează la fel, dar conceptul este puțin diferit, deoarece este un protocol fără conexiune, nu trebuie să vă conectați/ascultați pentru a trimite/primi pachete. Funcționează prin impunerea faptului că puteți primi pachete de la un server numai dacă acesta a răspuns mai întâi cu o politică validă cu eticheta allow-access-from domain
.
totul este atât de enervant, de ce există toate aceste lucruri?
caracteristicile de securitate socket și WWW există pentru a proteja persoanele care instalează Unity Web Player. Fără aceste restricții, ar fi posibil un atac precum următoarele:
- Bob lucrează la Casa Albă.
- Frank este rău. El scrie un Unity webgame care pretinde a fi un joc, dar în fundal face o cerere WWW la http://internal.whitehouse.gov/LocationOfNuclearBombs.pdf. intern.whitehouse.gov este un server care nu este accesibil de pe internet, dar este accesibil de la stația de lucru a lui Bob, deoarece lucrează la Casa Albă.
- Frank trimite acei octeți pdf la http://frank.com/secretDataUploader.php
- Frank plasează acest joc pe http://www.frank.com/coolgame.unity3d
- Frank îl convinge cumva pe Bob să joace jocul.
- Bob joacă jocul.
- jocul descarcă în tăcere documentul secret și îl trimite lui Frank.
cu caracteristicile de securitate WWW și socket, acest atac va eșua, deoarece înainte de a descărca pdf-ul, unitatea verifică http://internal.whitehouse.gov/crossdomain.xml, cu intenția de a cere acel server: „datele pe care le aveți pe serverul dvs. sunt disponibile pentru utilizare publică?”. Plasarea unui domeniu încrucișat.xml pe un server web poate fi văzut ca răspuns la această întrebare. În cazul acestui exemplu, operatorul de sistem de internal.whitehouse.gov nu va plasa un crossdomain.xml pe serverul său, ceea ce va conduce Unity să nu descarce pdf-ul.
din păcate, pentru a proteja persoanele care instalează Unity Web Player, persoanele care se dezvoltă în Unity trebuie să ia în considerare aceste măsuri de securitate atunci când dezvoltă conținut. Aceleași restricții sunt prezente în toate tehnologiile majore de pluginuri. (Flash, Silverlight, Shockwave)
excepții
pentru a găsi echilibrul corect între protejarea utilizatorilor playerului Web și ușurarea vieții dezvoltatorilor de conținut, am implementat o excepție de la mecanismul de securitate descris mai sus:
vi se permite să descărcați imagini de pe servere care nu au un domeniu încrucișat.fișier xml. Cu toate acestea, singurul lucru pe care vi se permite să-l faceți cu aceste imagini este să le folosiți ca texturi în scena dvs. Nu aveți voie să utilizați GetPixel () pe ele. De asemenea, nu aveți voie să citiți înapoi de pe ecran. Ambele încercări vor duce la aruncarea unei SecurityException:
SecurityException: No read access to the texture data: at (wrapper managed-to-native) UnityEngine.Texture2D:GetPixel (int,int)
raționamentul este aici este că este în regulă să descărcați imaginea, atâta timp cât dezvoltatorul de conținut nu are acces la ea. Deci, îl puteți afișa utilizatorului, dar nu puteți trimite octeții imaginii înapoi la un alt server. Dacă aveți nevoie de acces la datele pixelilor, plasați un fișier crossdomain.xml
pe serverul de unde sunt preluate imaginile.