for VS2010, need to include Shlobj.h instead of ShFolder.h
[moonshot.git] / moonshot / mech_eap / util_cred.c
index 1d49e56..40a8c11 100644 (file)
 
 #include "gssapiP_eap.h"
 
+#if defined(WIN32)
+/*This didn't work for me(Alexey) when Visual Studio 2005 Express is used: */
+#include <Shlobj.h>
+/*This didn't work for me(Kevin) when Visual Studio 2010 Express is used: */
+/*#include <ShFolder.h>*/
+
+#if !defined(snprintf)
+#define snprintf  _snprintf
+#endif
+
+#else
 #include <pwd.h>
+#endif
+#include <stdio.h> /* for BUFSIZ */
 
 OM_uint32
 gssEapAllocCred(OM_uint32 *minor, gss_cred_id_t *pCred)
@@ -116,9 +129,12 @@ readDefaultIdentityAndCreds(OM_uint32 *minor,
 {
     OM_uint32 major, tmpMinor;
     FILE *fp = NULL;
-    char pwbuf[BUFSIZ], buf[BUFSIZ];
+    char buf[BUFSIZ];
     char *ccacheName;
+#if !defined(WIN32)
+    char pwbuf[BUFSIZ];
     struct passwd *pw = NULL, pwd;
+#endif
 
     defaultIdentity->length = 0;
     defaultIdentity->value = NULL;
@@ -128,6 +144,7 @@ readDefaultIdentityAndCreds(OM_uint32 *minor,
 
     ccacheName = getenv("GSSEAP_IDENTITY");
     if (ccacheName == NULL) {
+#if !defined(WIN32)
         if (getpwuid_r(getuid(), &pwd, pwbuf, sizeof(pwbuf), &pw) != 0 ||
             pw == NULL || pw->pw_dir == NULL) {
             major = GSS_S_CRED_UNAVAIL;
@@ -137,6 +154,23 @@ readDefaultIdentityAndCreds(OM_uint32 *minor,
 
         snprintf(buf, sizeof(buf), "%s/.gss_eap_id", pw->pw_dir);
         ccacheName = buf;
+#else
+       TCHAR szPath[MAX_PATH];
+
+       if(!SUCCEEDED(SHGetFolderPath(NULL,
+                                     CSIDL_APPDATA, /* |CSIDL_FLAG_CREATE */
+                                     NULL, /* User access token */
+                                     0,    /* == SHGFP_TYPE_CURRENT from ShlObj.h */
+                                     szPath))) {
+            major = GSS_S_CRED_UNAVAIL;
+////Needs to be correctly converted from the GetLastError();
+            *minor = errno;
+            goto cleanup;
+       }
+
+        snprintf(buf, sizeof(buf), "%s/.gss_eap_id", szPath);
+        ccacheName = buf;
+#endif
     }
 
     fp = fopen(ccacheName, "r");
@@ -389,3 +423,69 @@ gssEapCredAvailable(gss_cred_id_t cred, gss_OID mech)
 
     return present;
 }
+
+OM_uint32
+gssEapInquireCred(OM_uint32 *minor,
+                  gss_cred_id_t cred,
+                  gss_name_t *name,
+                  OM_uint32 *pLifetime,
+                  gss_cred_usage_t *cred_usage,
+                  gss_OID_set *mechanisms)
+{
+    OM_uint32 major;
+    time_t now, lifetime;
+
+    if (name != NULL) {
+        major = gssEapDuplicateName(minor, cred->name, name);
+        if (GSS_ERROR(major))
+            return major;
+    }
+
+    if (cred_usage != NULL) {
+        OM_uint32 flags = (cred->flags & (CRED_FLAG_INITIATE | CRED_FLAG_ACCEPT));
+
+        switch (flags) {
+        case CRED_FLAG_INITIATE:
+            *cred_usage = GSS_C_INITIATE;
+            break;
+        case CRED_FLAG_ACCEPT:
+            *cred_usage = GSS_C_ACCEPT;
+            break;
+        default:
+            *cred_usage = GSS_C_BOTH;
+            break;
+        }
+    }
+
+    if (mechanisms != NULL) {
+        if (cred->mechanisms != GSS_C_NO_OID_SET)
+            major = duplicateOidSet(minor, cred->mechanisms, mechanisms);
+        else
+            major = gssEapIndicateMechs(minor, mechanisms);
+        if (GSS_ERROR(major))
+            return major;
+    }
+
+    if (cred->expiryTime == 0) {
+        lifetime = GSS_C_INDEFINITE;
+    } else  {
+        now = time(NULL);
+        lifetime = now - cred->expiryTime;
+        if (lifetime < 0)
+            lifetime = 0;
+    }
+
+    if (pLifetime != NULL) {
+        *pLifetime = lifetime;
+    }
+
+    if (lifetime == 0) {
+        *minor = GSSEAP_CRED_EXPIRED;
+        return GSS_S_CREDENTIALS_EXPIRED;
+    }
+
+    major = GSS_S_COMPLETE;
+    *minor = 0;
+
+    return major;
+}