Anteckning
Åtkomst till den här sidan kräver auktorisering. Du kan prova att logga in eller ändra kataloger.
Åtkomst till den här sidan kräver auktorisering. Du kan prova att ändra kataloger.
Den här artikeln beskriver Windows Hello-tekniken som levereras som en del av Windows och beskriver hur utvecklare kan implementera den här tekniken för att skydda sina Windows-appar och serverdelstjänster. Den belyser specifika funktioner i dessa tekniker som hjälper till att minimera hot som uppstår vid användning av konventionella autentiseringsuppgifter och ger vägledning om hur du utformar och distribuerar dessa tekniker som en del av en Windows-klientdistribution.
Anmärkning
Den här artikeln fokuserar på apputveckling. Information om arkitektur och implementeringsinformation för Windows Hello finns i Planera en Windows Hello för företag-distribution.
En stegvis genomgång av hur du skapar en WinUI-app med Windows Hello och tjänsten för säkerhetskopieringsautentisering finns i artiklarna om Inloggningsappen för Windows Hello och Windows Hello-inloggningstjänsten .
Inledning
Ett grundläggande antagande om informationssäkerhet är att ett system kan identifiera vem som använder det. Genom att identifiera en användare kan systemet avgöra om användaren identifieras på rätt sätt (en process som kallas autentisering) och sedan bestämma vad en korrekt autentiserad användare ska kunna göra (auktorisering). Den överväldigande majoriteten av datorsystem som distribueras över hela världen är beroende av användarautentiseringsuppgifter för att fatta autentiserings- och auktoriseringsbeslut, vilket innebär att dessa system är beroende av återanvändbara, användarskapade lösenord som grund för deras säkerhet. Den ofta citerade maximen att autentisering kan omfatta "något du vet, något du har eller något du är" markerar snyggt problemet: ett återanvändbart lösenord är en autentiseringsfaktor helt själv, så alla som känner till lösenordet kan personifiera den användare som äger det.
Problem med traditionella autentiseringsuppgifter
Ända sedan mitten av 1960-talet, när Fernando Corbató och hans team vid Massachusetts Institute of Technology förespråkade införandet av lösenordet, har användare och administratörer varit tvungna att hantera användningen av lösenord för användarautentisering och auktorisering. Med tiden har den senaste tekniken för lösenordslagring och användning avancerat något (med säker hashning och saltning, till exempel), men vi står fortfarande inför två problem. Lösenord är lätta att klona och de är lätta att stjäla. Dessutom kan implementeringsfel göra dem osäkra och användarna har svårt att balansera bekvämlighet och säkerhet.
Stöld av autentiseringsuppgifter
Den största risken med lösenord är enkel: en angripare kan enkelt stjäla dem. Varje plats där ett lösenord anges, bearbetas eller lagras är sårbart. En angripare kan till exempel stjäla en samling lösenord eller hashvärden från en autentiseringsserver genom att tjuvlyssna på nätverkstrafiken till en programserver, genom att implantera skadlig kod i ett program eller på en enhet, genom att logga användarens tangenttryckningar på en enhet eller genom att titta på vilka tecken en användare skriver. Det här är bara de vanligaste angreppsmetoderna.
En annan relaterad risk är uppspelning av autentiseringsuppgifter, där en angripare samlar in en giltig autentiseringsuppgift genom att tjuvlyssna på ett osäkert nätverk och sedan spelar upp den senare för att personifiera en giltig användare. De flesta autentiseringsprotokoll (inklusive Kerberos och OAuth) skyddar mot uppspelningsattacker genom att inkludera en tidsstämpel i utbytesprocessen för autentiseringsuppgifter, men den taktiken skyddar bara den token som autentiseringssystemet utfärdar, inte lösenordet som användaren tillhandahåller för att få biljetten i första hand.
Återanvändning av autentiseringsuppgifter
Den vanliga metoden att använda en e-postadress som användarnamn gör ett dåligt problem värre. En angripare som har återställt ett par med användarnamn och lösenord från ett komprometterat system kan sedan prova samma par i andra system. Den här taktiken fungerar förvånansvärt ofta för att tillåta angripare att springboard från ett komprometterat system till andra system. Användningen av e-postadresser som användarnamn leder till ytterligare problem som vi kommer att utforska senare i den här guiden.
Lösa problem med autentiseringsuppgifter
Det är svårt att lösa de problem som lösenord utgör. Att bara strama åt lösenordsprinciperna kommer inte att göra det. användare kan bara återanvända, dela eller skriva ned lösenord. Även om användarutbildning är avgörande för autentiseringssäkerhet eliminerar inte enbart utbildning problemet.
Windows Hello ersätter lösenord med stark tvåfaktorautentisering (2FA) genom att verifiera befintliga autentiseringsuppgifter och genom att skapa en enhetsspecifik autentiseringsuppgift som en biometrisk eller PIN-baserad användargest skyddar.
Vad är Windows Hello?
Windows Hello är ett biometriskt inloggningssystem inbyggt i Windows som gör att du kan använda ditt ansikte, fingeravtryck eller en PIN-kod för att låsa upp enheten. Det ersätter traditionella lösenord med en säkrare och bekvämare metod. Dina biometriska data lagras säkert på enheten, och även om någon stjäl din enhet kan de inte komma åt dem utan din PIN-kod eller biometriska gest. När du är upplåst kan du komma åt dina appar, data och tjänster sömlöst.
Windows Hello-autentiseringen kallas hello. Varje Hello är unikt för en specifik användare och enhet. Den synkroniseras inte mellan enheter eller delar data med servrar eller appar. Om flera personer använder samma enhet måste varje person konfigurera sin egen Windows Hello-konfiguration. Den här konfigurationen är kopplad till deras autentiseringsuppgifter på den specifika enheten. Tänk på en Hello som en nyckel som låser upp dina lagrade autentiseringsuppgifter, som sedan används för att logga in på appar eller tjänster. Det är inte en egen autentiseringsuppgift utan fungerar som ett andra säkerhetslager under autentiseringen.
Windows Hello-autentisering
Windows Hello är ett robust sätt för en enhet att identifiera en enskild användare, som hanterar den första delen av sökvägen mellan en användare och en begärd tjänst eller ett dataobjekt. När enheten har identifierat användaren måste den fortfarande autentisera användaren innan den avgör om den ska bevilja åtkomst till en begärd resurs. Windows Hello tillhandahåller stark 2FA som är helt integrerad i Windows och ersätter återanvändbara lösenord med kombinationen av en specifik enhet och en biometrisk gest eller PIN-kod.
Windows Hello är dock inte bara en ersättning för traditionella 2FA-system. Det är konceptuellt likt smartkort: autentisering utförs med hjälp av kryptografiska primitiver i stället för strängjämförelser, och användarens nyckelmaterial är säkert inuti manipuleringsbeständig maskinvara. Windows Hello kräver inte heller de extra infrastrukturkomponenter som krävs för smartkortsdistribution. I synnerhet behöver du inte en PKI (Public Key Infrastructure) för att hantera certifikat, om du inte har något för närvarande. Windows Hello kombinerar de största fördelarna med smartkort – flexibilitet för distribution av virtuella smartkort och robust säkerhet för fysiska smartkort – utan några nackdelar.
Så här fungerar Windows Hello
När användaren konfigurerar Windows Hello på sin dator genererar det ett nytt offentligt–privat nyckelpar på enheten. Den betrodda plattformsmodulen (TPM) genererar och skyddar den här privata nyckeln. Om enheten inte har något TPM-chip krypteras och skyddas den privata nyckeln av programvara. Dessutom genererar TPM-aktiverade enheter ett datablock som kan användas för att intyga att en nyckel är bunden till TPM. Den här attesteringsinformationen kan användas i din lösning för att avgöra om användaren till exempel beviljas en annan auktoriseringsnivå.
Om du vill aktivera Windows Hello på en enhet måste användaren antingen ha sitt Microsoft Entra-ID-konto eller Ett Microsoft-konto anslutet i Windows-inställningarna.
Så här skyddas nycklar
Varje gång nyckelmaterial genereras måste det skyddas mot angrepp. Det mest robusta sättet att göra detta är genom specialiserad maskinvara. Det finns en lång historia av att använda maskinvarusäkerhetsmoduler (HSM) för att generera, lagra och bearbeta nycklar för säkerhetskritiska program. Smartkort är en särskild typ av HSM, liksom enheter som är kompatibla med TPM-standarden för betrodd databehandlingsgrupp. När det är möjligt drar Windows Hello-implementeringen nytta av inbyggd TPM-maskinvara för att generera, lagra och bearbeta nycklar. Windows Hello och Windows Hello for Work kräver dock ingen inbyggd TPM.
När det är möjligt rekommenderar Microsoft användning av TPM-maskinvara. TPM skyddar mot en mängd olika kända och potentiella attacker, inklusive BRUTE-force-attacker med PIN-kod. TPM ger även ytterligare ett skyddslager efter en kontoutelåsning. När TPM har låst nyckelmaterialet måste användaren återställa PIN-koden. Återställning av PIN-koden innebär att alla nycklar och certifikat som krypterats med det gamla nyckelmaterialet tas bort.
Autentisering
När en användare vill komma åt skyddat nyckelmaterial börjar autentiseringsprocessen med att användaren anger en PIN-kod eller biometrisk gest för att låsa upp enheten, en process som ibland kallas "frigöra nyckeln".
Ett program kan aldrig använda nycklarna från ett annat program och ingen kan heller använda nycklarna från en annan användare. Dessa nycklar används för att signera begäranden som skickas till identitetsprovidern eller IDP:t för att få åtkomst till angivna resurser. Program kan använda specifika API:er för att begära åtgärder som kräver nyckelmaterial för specifika åtgärder. Åtkomst via dessa API:er kräver explicit validering via en användargest och nyckelmaterialet exponeras inte för det begärande programmet. I stället ber programmet om en specifik åtgärd som att signera en databit, och Windows Hello-lagret hanterar det faktiska arbetet och returnerar resultatet.
Gör dig redo att implementera Windows Hello
Nu när vi har en grundläggande förståelse för hur Windows Hello fungerar kan vi ta en titt på hur du implementerar dem i våra egna program.
Det finns olika scenarier som vi kan implementera med Windows Hello. Du kan till exempel bara logga in på din app på en enhet. Det andra vanliga scenariot är att autentisera mot en tjänst. I stället för att använda ett inloggningsnamn och lösenord använder du Windows Hello. I följande avsnitt går vi igenom hur du implementerar ett par olika scenarier, bland annat hur du autentiserar mot dina tjänster med Windows Hello och hur du konverterar från ett befintligt användarnamn/lösenordssystem till ett Windows Hello-system.
Implementering av Windows Hello
I det här avsnittet börjar vi med ett greenfield-scenario utan ett befintligt autentiseringssystem, och vi förklarar hur du implementerar Windows Hello.
I nästa avsnitt beskrivs hur du migrerar från ett befintligt användarnamn/lösenordssystem. Men även om det avsnittet intresserar dig mer kan du titta igenom det här för att få en grundläggande förståelse för processen och den kod som krävs.
Registrera nya användare
Vi börjar med en helt ny tjänst som använder Windows Hello och en hypotetisk ny användare som är redo att registrera sig på en ny enhet.
Det första steget är att kontrollera att användaren kan använda Windows Hello. Appen verifierar användarinställningar och datorfunktioner för att se till att den kan skapa användar-ID-nycklar. Om appen fastställer att användaren ännu inte har aktiverat Windows Hello uppmanas användaren att konfigurera detta innan appen används.
För att aktivera Windows Hello behöver användaren bara konfigurera en PIN-kod i Windows-inställningar, såvida inte användaren konfigurerade den under OOBE (Out of Box Experience).
Följande kodrader visar ett enkelt sätt att kontrollera om användaren har konfigurerats för Windows Hello.
var keyCredentialAvailable = await KeyCredentialManager.IsSupportedAsync();
if (!keyCredentialAvailable)
{
// User didn't set up PIN yet
return;
}
Nästa steg är att be användaren om information för att registrera sig med din tjänst. Du kan välja att be användaren om förnamn, efternamn, e-postadress och ett unikt användarnamn. Du kan använda e-postadressen som unik identifierare. det är upp till dig.
I det här scenariot använder vi e-postadressen som unik identifierare för användaren. När användaren har registrerat sig bör du överväga att skicka ett valideringsmeddelande för att säkerställa att adressen är giltig. Detta ger dig en mekanism för att återställa kontot om det behövs.
Om användaren har konfigurerat sin PIN-kod skapar appen användarens KeyCredential. Appen hämtar också den valfria informationen om nyckelattestering för att hämta kryptografiska bevis på att nyckeln genereras på TPM. Den genererade offentliga nyckeln och eventuellt attesteringen skickas till backend-servern för registrering av enheten som används. Varje nyckelpar som genereras på varje enhet kommer att vara unikt.
Koden för att skapa KeyCredential ser ut så här:
var keyCreationResult = await KeyCredentialManager.RequestCreateAsync(
AccountId, KeyCredentialCreationOption.ReplaceExisting);
RequestCreateAsync är anropet som skapar den offentliga och privata nyckeln. Om enheten har rätt TPM-chip begär API:erna TPM-chipet för att skapa den privata och offentliga nyckeln och lagra resultatet. Om det inte finns något TPM-chip tillgängligt skapar operativsystemet nyckelparet i koden. Det finns inget sätt för appen att komma åt de skapade privata nycklarna direkt. En del av skapandet av nyckelparen är också den resulterande attesteringsinformationen. (Mer information om attestering finns i nästa avsnitt.)
När nyckelparet och attesteringsinformationen har skapats på enheten måste den offentliga nyckeln, den valfria attesteringsinformationen och den unika identifieraren (till exempel e-postadressen) skickas till serverdelsregistreringstjänsten och lagras i serverdelen.
För att användaren ska kunna komma åt appen på flera enheter måste serverdelstjänsten kunna lagra flera nycklar för samma användare. Eftersom varje nyckel är unik för varje enhet lagrar vi alla dessa nycklar som är anslutna till samma användare. En enhetsidentifierare används för att optimera serverdelen när användare autentiseras. Vi pratar mer detaljerat om detta i nästa avsnitt.
Ett exempeldatabasschema för att lagra den här informationen på serverdelen kan se ut så här:
Registreringslogik kan se ut så här:
Den registreringsinformation som du samlar in kan naturligtvis innehålla mycket mer identifierande information än vi tar med i det här enkla scenariot. Om din app till exempel har åtkomst till en säker tjänst, till exempel en för banktjänster, måste du begära identitetsbevis och andra saker som en del av registreringsprocessen. När alla villkor är uppfyllda lagras den offentliga nyckeln för den här användaren i serverdelen och används för att verifiera nästa gång användaren använder tjänsten.
using System;
using System.Runtime;
using System.Threading.Tasks;
using Windows.Storage.Streams;
using Windows.Security.Credentials;
static async void RegisterUser(string AccountId)
{
var keyCredentialAvailable = await KeyCredentialManager.IsSupportedAsync();
if (!keyCredentialAvailable)
{
// The user didn't set up a PIN yet
return;
}
var keyCreationResult = await KeyCredentialManager.RequestCreateAsync(AccountId, KeyCredentialCreationOption.ReplaceExisting);
if (keyCreationResult.Status == KeyCredentialStatus.Success)
{
var userKey = keyCreationResult.Credential;
var publicKey = userKey.RetrievePublicKey();
var keyAttestationResult = await userKey.GetAttestationAsync();
IBuffer keyAttestation = null;
IBuffer certificateChain = null;
bool keyAttestationIncluded = false;
bool keyAttestationCanBeRetrievedLater = false;
keyAttestationResult = await userKey.GetAttestationAsync();
KeyCredentialAttestationStatus keyAttestationRetryType = 0;
switch (keyAttestationResult.Status)
{
case KeyCredentialAttestationStatus.Success:
keyAttestationIncluded = true;
keyAttestation = keyAttestationResult.AttestationBuffer;
certificateChain = keyAttestationResult.CertificateChainBuffer;
break;
case KeyCredentialAttestationStatus.TemporaryFailure:
keyAttestationRetryType = KeyCredentialAttestationStatus.TemporaryFailure;
keyAttestationCanBeRetrievedLater = true;
break;
case KeyCredentialAttestationStatus.NotSupported:
keyAttestationRetryType = KeyCredentialAttestationStatus.NotSupported;
keyAttestationCanBeRetrievedLater = true;
break;
}
}
else if (keyCreationResult.Status == KeyCredentialStatus.UserCanceled ||
keyCreationResult.Status == KeyCredentialStatus.UserPrefersPassword)
{
// Show error message to the user to get confirmation that user
// does not want to enroll.
}
}
Attest
När du skapar nyckelparet finns det också ett alternativ för att begära attesteringsinformationen, som genereras av TPM-chipet. Den här valfria informationen kan skickas till servern som en del av registreringsprocessen. TPM-nyckelattestering är ett protokoll som kryptografiskt bevisar att en nyckel är TPM-bunden. Den här typen av attestering kan användas för att garantera att en viss kryptografisk åtgärd inträffade i TPM för en viss dator.
När den tar emot den genererade RSA-nyckeln, attesteringsinstrukeringen och AIK-certifikatet verifierar servern följande villkor:
- AIK-certifikatsignaturen är giltig.
- AIK-certifikatet kedjar sig till en betrodd rot.
- AIK-certifikatet och dess kedja är aktiverade för EKU OID "2.23.133.8.3" (eget namn är "Attesteringsidentitetsnyckelcertifikat").
- AIK-certifikatet är tidsgiltigt.
- Alla utfärdande CA-certifikat i kedjan är tidsgiltigt och återkallas inte.
- Attesteringsuttalandet är korrekt utformat.
- Signaturen på KeyAttestation Blob använder en offentlig AIK-nyckel.
- Den offentliga nyckeln som ingår i KeyAttestation-bloben matchar den offentliga RSA-nyckel som klienten skickade tillsammans med attesteringsinstrukeringen.
Din app kan tilldela användaren en annan auktoriseringsnivå, beroende på dessa villkor. Om en av dessa kontroller till exempel misslyckas kanske den inte registrerar användaren eller så kan den begränsa vad användaren kan göra.
Logga in med Windows Hello
När användaren har registrerats i systemet kan han eller hon använda appen. Beroende på scenariot kan du be användarna att autentisera innan de kan börja använda appen eller bara be dem att autentisera när de börjar använda dina serverdelstjänster.
Tvinga användaren att logga in igen
I vissa scenarier kanske du vill att användaren ska bevisa att han eller hon är den person som för närvarande är inloggad, innan du kommer åt appen eller ibland innan du utför en viss åtgärd i din app. Innan en bankapp till exempel skickar kommandot för överföringspengar till servern vill du se till att det är användaren, i stället för någon som hittade en inloggad enhet, som försöker utföra en transaktion. Du kan tvinga användaren att logga in igen i din app med hjälp av klassen UserConsentVerifier . Följande kodrad tvingar användaren att ange sina autentiseringsuppgifter.
Följande kodrad tvingar användaren att ange sina autentiseringsuppgifter.
UserConsentVerificationResult consentResult = await UserConsentVerifier.RequestVerificationAsync("userMessage");
if (consentResult.Equals(UserConsentVerificationResult.Verified))
{
// continue
}
Du kan också använda mekanismen för utmaningssvar från servern, som kräver att en användare anger sin PIN-kod eller sina biometriska autentiseringsuppgifter. Det beror på vilket scenario du som utvecklare behöver implementera. Den här mekanismen beskrivs i följande avsnitt.
Autentisering på serverdelen
När appen försöker komma åt en skyddad serverdelstjänst skickar tjänsten en utmaning till appen. Appen använder den privata nyckeln från användaren för att signera utmaningen och skickar tillbaka den till servern. Eftersom servern har lagrat den offentliga nyckeln för den användaren använder den vanliga krypto-API:er för att se till att meddelandet verkligen har signerats med rätt privat nyckel. På klienten görs signeringen av Windows Hello-API:erna. utvecklaren kommer aldrig att ha åtkomst till någon användares privata nyckel.
Förutom att kontrollera nycklarna kan tjänsten också kontrollera nyckelattesteringen och se om det finns några begränsningar som anropas för hur nycklarna lagras på enheten. När enheten till exempel använder TPM för att skydda nycklarna är det säkrare än enheter som lagrar nycklarna utan TPM. Serverdelslogik kan till exempel avgöra att användaren endast får överföra en viss summa pengar när ingen TPM används för att minska riskerna.
Attestering är endast tillgängligt för enheter med ett TPM-chip som är version 2.0 eller senare. Därför måste du ta hänsyn till att den här informationen kanske inte är tillgänglig på alla enheter.
Klientarbetsflödet kan se ut som i följande diagram:
När appen anropar tjänsten på serverdelen skickar servern en utmaning. Utmaningen signeras med följande kod:
var openKeyResult = await KeyCredentialManager.OpenAsync(AccountId);
if (openKeyResult.Status == KeyCredentialStatus.Success)
{
var userKey = openKeyResult.Credential;
var publicKey = userKey.RetrievePublicKey();
var signResult = await userKey.RequestSignAsync(message);
if (signResult.Status == KeyCredentialStatus.Success)
{
return signResult.Result;
}
else if (signResult.Status == KeyCredentialStatus.UserPrefersPassword)
{
}
}
Den första raden , KeyCredentialManager.OpenAsync, ber Windows att öppna nyckelhandtaget. Om det lyckas kan du signera utmaningsmeddelandet med metoden KeyCredential.RequestSignAsync , vilket gör att Windows begär användarens PIN-kod eller biometri via Windows Hello. Utvecklaren har inte vid något tillfälle åtkomst till användarens privata nyckel. Allt detta hålls säkert via API:erna.
API:erna begär att Windows signerar utmaningen med den privata nyckeln. Systemet ber sedan användaren om en PIN-kod eller en konfigurerad biometrisk inloggning. När rätt information anges kan systemet be TPM-chipet att utföra kryptografiska funktioner och signera utmaningen. (Eller använd reservprogramvaran om det inte finns någon TPM tillgänglig). Klienten måste skicka tillbaka den signerade utmaningen till servern.
Ett grundläggande flöde för utmaning–svar visas i det här sekvensdiagrammet:
Därefter måste servern verifiera signaturen. När du begär den offentliga nyckeln och skickar den till servern för framtida validering finns den i en ASN.1-kodad publicKeyInfo-blob. Om du undersöker Windows Hello-kodexemplet på GitHub ser du att det finns hjälpklasser för att omsluta Crypt32-funktioner för att översätta DEN ASN.1-kodade bloben till en CNG-blob, som används oftare. Blobben innehåller algoritmen för offentlig nyckel, som är RSA, och den offentliga RSA-nyckeln.
I exemplet är anledningen till att vi konverterar den ASN.1-kodade bloben till en CNG-blob så att den kan användas med CNG och BCrypt-API:et. Om du letar upp CNG-bloben pekar den dig till den relaterade BCRYPT_KEY_BLOB-strukturen. Den här API-ytan kan användas för autentisering och kryptering i Windows-program. ASN.1 är en dokumenterad standard för kommunikation av datastrukturer som kan serialiseras och används ofta i kryptering med offentliga nycklar och med certifikat. Därför returneras den offentliga nyckelinformationen på det här sättet. Den offentliga nyckeln är en RSA-nyckel. och det är den algoritm som Windows Hello använder när data signeras.
När du har CNG-bloben måste du verifiera den signerade utmaningen mot användarens offentliga nyckel. Eftersom alla använder sitt eget system eller serverdelsteknik finns det inget allmänt sätt att implementera den här logiken. Vi använder SHA256 som hash-algoritm och Pkcs1 för SignaturePadding, så se till att det är det du använder när du verifierar det signerade svaret från klienten. Se exemplet igen för ett sätt att göra det på servern i .NET 4.6, men i allmänhet ser det ut ungefär så här:
using (RSACng pubKey = new RSACng(publicKey))
{
retval = pubKey.VerifyData(originalChallenge, responseSignature, HashAlgorithmName.SHA256, RSASignaturePadding.Pkcs1);
}
Vi läser den lagrade offentliga nyckeln, som är en RSA-nyckel. Vi validerar det signerade utmaningsmeddelandet med den offentliga nyckeln och om detta checkar ut godkänner vi användaren. Om användaren autentiseras kan appen anropa serverdelstjänsterna som vanligt.
Den fullständiga koden kan se ut ungefär så här:
using System;
using System.Runtime;
using System.Threading.Tasks;
using Windows.Storage.Streams;
using Windows.Security.Cryptography;
using Windows.Security.Cryptography.Core;
using Windows.Security.Credentials;
static async Task<IBuffer> GetAuthenticationMessageAsync(IBuffer message, String AccountId)
{
var openKeyResult = await KeyCredentialManager.OpenAsync(AccountId);
if (openKeyResult.Status == KeyCredentialStatus.Success)
{
var userKey = openKeyResult.Credential;
var publicKey = userKey.RetrievePublicKey();
var signResult = await userKey.RequestSignAsync(message);
if (signResult.Status == KeyCredentialStatus.Success)
{
return signResult.Result;
}
else if (signResult.Status == KeyCredentialStatus.UserCanceled)
{
// Launch app-specific flow to handle the scenario
return null;
}
}
else if (openKeyResult.Status == KeyCredentialStatus.NotFound)
{
// PIN reset has occurred somewhere else and key is lost.
// Repeat key registration
return null;
}
else
{
// Show custom UI because unknown error has happened.
return null;
}
}
Implementeringen av rätt mekanism för utmaning–svar ligger utanför omfånget för det här dokumentet, men det här avsnittet är något som kräver uppmärksamhet för att kunna skapa en säker mekanism för att förhindra sådant som återuppspelningsattacker eller man-in-the-middle-attacker.
Registrera en annan enhet
Det är vanligt att användare har flera enheter med samma appar installerade idag. Hur fungerar detta när du använder Windows Hello med flera enheter?
När du använder Windows Hello skapar varje enhet en unik privat och offentlig nyckeluppsättning. Det innebär att om du vill att en användare ska kunna använda flera enheter måste serverdelen kunna lagra flera offentliga nycklar från den här användaren. Se databasdiagrammet i avsnittet Registrera nya användare för ett exempel på tabellstrukturen.
Att registrera en annan enhet är nästan detsamma som att registrera en användare för första gången. Du måste fortfarande se till att användaren som registrerar sig för den här nya enheten verkligen är den användare som de påstår sig vara. Du kan göra det med valfri tvåfaktorautentiseringsmekanism som används idag. Det finns flera sätt att åstadkomma detta på ett säkert sätt. Allt beror på ditt scenario.
Om du till exempel fortfarande använder inloggningsnamn och lösenord kan du använda det för att autentisera användaren och be dem att använda någon av sina verifieringsmetoder som SMS eller e-post. Om du inte har något inloggningsnamn och lösenord kan du också använda en av de redan registrerade enheterna och skicka ett meddelande till appen på den enheten. MSA-autentiseringsappen är ett exempel på detta. Kort och gott bör du använda en vanlig 2FA-mekanism för att registrera extra enheter för användaren.
Koden för att registrera den nya enheten är exakt samma som att registrera användaren för första gången (inifrån appen).
var keyCreationResult = await KeyCredentialManager.RequestCreateAsync(
AccountId, KeyCredentialCreationOption.ReplaceExisting);
För att göra det enklare för användaren att känna igen vilka enheter som är registrerade kan du välja att skicka enhetsnamnet eller en annan identifierare som en del av registreringen. Detta är också användbart, till exempel om du vill implementera en tjänst på serverdelen där användare kan avregistrera enheter när en enhet går förlorad.
Använda flera konton i din app
Förutom att stödja flera enheter för ett enda konto är det också vanligt att ha stöd för flera konton i en enda app. Du kanske till exempel ansluter till flera Twitter-konton från din app. Med Windows Hello kan du skapa flera nyckelpar och stödja flera konton i din app.
Ett sätt att göra detta är att behålla användarnamnet eller den unika identifieraren som beskrivs i föregående avsnitt om isolerad lagring. Därför lagrar du konto-ID:t i isolerad lagring varje gång du skapar ett nytt konto.
I appens användargränssnitt låter du användaren antingen välja ett av de tidigare skapade kontona eller registrera sig med ett nytt. Flödet för att skapa ett nytt konto är detsamma som beskrivits tidigare. Att välja ett konto handlar om att lista de lagrade kontona på skärmen. När användaren har valt ett konto använder du konto-ID:t för att logga in på användaren i din app:
var openKeyResult = await KeyCredentialManager.OpenAsync(AccountId);
Resten av flödet är detsamma som beskrevs tidigare. För att vara tydlig skyddas alla dessa konton av samma PIN-kod eller biometriska gest eftersom de i det här scenariot används på en enda enhet med samma Windows-konto.
Migrera ett befintligt system till Windows Hello
I det här korta avsnittet behandlar vi en befintlig paketerad app och ett serverdelssystem som använder en databas som lagrar användarnamnet och hash-lösenordet. Dessa appar samlar in autentiseringsuppgifter från användaren när appen startar och använder dem när serverdelssystemet returnerar autentiseringsuppgiften.
Här beskriver vi vilka delar som behöver ändras eller ersättas för att Windows Hello ska fungera.
Vi har redan beskrivit de flesta av teknikerna i de tidigare avsnitten. Att lägga till Windows Hello i ditt befintliga system innebär att du lägger till ett par olika flöden i registrerings- och autentiseringsdelen av koden.
En metod är att låta användaren välja när den ska uppgraderas. När användaren har loggat in på appen och du upptäcker att appen och operativsystemet kan stödja Windows Hello kan du fråga användaren om han eller hon vill uppgradera autentiseringsuppgifterna för att använda det här moderna och säkrare systemet. Du kan använda följande kod för att kontrollera om användaren kan använda Windows Hello.
var keyCredentialAvailable = await KeyCredentialManager.IsSupportedAsync();
Användargränssnittet kan se ut ungefär så här:
Om användaren väljer att börja använda Windows Hello skapar du den KeyCredential som beskrevs tidigare. Registreringsservern i backend lägger till den publika nyckeln och det valfria attestationsutlåtandet i databasen. Eftersom användaren redan är autentiserad med användarnamn och lösenord kan servern länka de nya autentiseringsuppgifterna till den aktuella användarinformationen i databasen. Databasmodellen kan vara samma som exemplet som beskrevs tidigare.
Om appen kunde skapa användarna KeyCredential lagrar den användar-ID:t i isolerad lagring så att användaren kan välja det här kontot från listan när appen har startats igen. Från och med nu följer flödet exakt de exempel som beskrivs i tidigare avsnitt.
Det sista steget när du migrerar till ett fullständigt Windows Hello-scenario är att inaktivera alternativet inloggningsnamn och lösenord i appen och ta bort lagrade hashade lösenord från databasen.
Sammanfattning
Windows introducerar en högre säkerhetsnivå som också är enkel att omsätta i praktiken. Windows Hello tillhandahåller ett nytt biometriskt inloggningssystem som identifierar användaren och aktivt motverkar försök att kringgå korrekt identifiering. Den kan sedan leverera flera lager med nycklar och certifikat som aldrig kan avslöjas eller användas utanför den betrodda plattformsmodulen. Dessutom finns ytterligare ett säkerhetslager tillgängligt via valfri användning av attesteringsidentitetsnycklar och certifikat.
Som utvecklare kan du använda den här vägledningen om design och distribution av dessa tekniker för att enkelt lägga till säker autentisering i dina paketerade Windows-appdistributioner för att skydda appar och serverdelstjänster. Den kod som krävs är minimal och lätt att förstå. Windows utför det krävande arbetet.
Flexibla implementeringsalternativ gör att Windows Hello kan ersätta eller fungera tillsammans med ditt befintliga autentiseringssystem. Implementeringsupplevelsen är smärtfri och kostnadseffektiv. Ingen ytterligare infrastruktur krävs för att distribuera Windows-säkerhet. Med Microsoft Hello inbyggt i operativsystemet erbjuder Windows den säkraste lösningen på de autentiseringsproblem som den moderna utvecklaren står inför.
Uppdraget slutfört! Du har precis gjort Internet till en säkrare plats!
Ytterligare resurser
Artiklar och exempelkod
- Översikt över Windows Hello
- Planera en Windows Hello för företag-distribution
- Windows Hello UWP-kodexempel på GitHub
Terminologi
Begrepp | Definition |
---|---|
AIK | En attesteringsidentitetsnyckel används för att tillhandahålla ett sådant kryptografiskt bevis (TPM-nyckelattestering) genom att signera egenskaperna för den icke-migrerande nyckeln och tillhandahålla egenskaperna och signaturen till den förlitande parten för verifiering. Den resulterande signaturen kallas för en "attestationsuttalande". Eftersom signaturen skapas med hjälp av den privata AIK-nyckeln – som bara kan användas i den TPM som skapade den – kan den förlitande parten lita på att den intygade nyckeln verkligen inte kan migreras och inte kan användas utanför den TPM:n. |
AIK-certifikat | Ett AIK-certifikat används för att intyga förekomsten av en AIK i en TPM. Det används också för att intyga att andra nycklar som certifierats av AIK kommer från den specifika TPM:n. |
IDP | En IDP är en identitetsprovider. Ett exempel är IDP-uppbyggnaden av Microsoft för Microsoft-konton. Varje gång ett program behöver autentiseras med en MSA kan det anropa MSA IDP. |
PKI | Infrastruktur för offentliga nycklar används ofta för att peka på en miljö som hanteras av själva organisationen och ansvarar för att skapa nycklar, återkalla nycklar osv. |
TPM | Den betrodda plattformsmodulen kan användas för att skapa kryptografiska offentliga/privata nyckelpar på ett sådant sätt att den privata nyckeln aldrig kan avslöjas eller användas utanför TPM (dvs. nyckeln kan inte migreras). |
TPM-nyckelattestering | Ett protokoll som kryptografiskt bevisar att en nyckel är TPM-bunden. Den här typen av attestering kan användas för att garantera att en viss kryptografisk åtgärd inträffade i TPM på en viss dator |
Relaterade ämnen
Windows developer