[prev in list] [next in list] [prev in thread] [next in thread]
List: kde-core-devel
Subject: KUser windows port and small API changes
From: "Nhuh Put" <nhuh.put () web ! de>
Date: 2007-09-22 23:40:59
Message-ID: 001901c7fd72$1b29ece0$8a96b053 () spika
[Download RAW message or body]
Hello
I would like to commit this patch on next Monday.
It's a Windows Port of KUser.
As things like room number and phone number are not available on windows, I
removed those methods and added a generic extendedProperty(const QByteArray)
This is only used in one place in kdebase, I would port the user.
I would also rename kuser.cpp to kuser_unix.cpp
PutHuhn
["kuser.patch" (text/x-patch)]
Index: kuser.cpp
===================================================================
--- kuser.cpp (revision 715697)
+++ kuser.cpp (working copy)
@@ -34,8 +34,8 @@
uid_t uid;
gid_t gid;
QString loginName, fullName;
- QString roomNumber, workPhone, homePhone;
QString homeDir, shell;
+ QMap<const QByteArray, QVariant> extendedProperties;
Private() : uid(uid_t(-1)), gid(gid_t(-1)) {}
Private(const char *name) : uid(uid_t(-1)), gid(gid_t(-1))
@@ -60,9 +60,9 @@
gid = p->pw_gid;
loginName = QString::fromLocal8Bit(p->pw_name);
fullName = gecosList[0];
- roomNumber = gecosList[1];
- workPhone = gecosList[2];
- homePhone = gecosList[3];
+ extendedProperties["roomnumber"] = QVariant(gecosList[1]);
+ extendedProperties["workphone"] = QVariant(gecosList[2]);
+ extendedProperties["homephone"] = QVariant(gecosList[3]);
homeDir = QString::fromLocal8Bit(p->pw_dir);
shell = QString::fromLocal8Bit(p->pw_shell);
}
@@ -85,7 +85,7 @@
}
}
-KUser::KUser(uid_t _uid)
+KUser::KUser(K_UID _uid)
: d(new Private( ::getpwuid( _uid ) ))
{
}
@@ -128,11 +128,11 @@
return uid() != uid_t(-1);
}
-uid_t KUser::uid() const {
+const K_UID KUser::uid() const {
return d->uid;
}
-gid_t KUser::gid() const {
+const K_GID KUser::gid() const {
return d->gid;
}
@@ -148,18 +148,6 @@
return d->fullName;
}
-QString KUser::roomNumber() const {
- return d->roomNumber;
-}
-
-QString KUser::workPhone() const {
- return d->workPhone;
-}
-
-QString KUser::homePhone() const {
- return d->homePhone;
-}
-
QString KUser::homeDir() const {
return d->homeDir;
}
@@ -194,6 +182,10 @@
return result;
}
+QVariant KUser::extendedProperty(const QByteArray &which) const
+{
+ return d->extendedProperties.value(which);
+}
QList<KUser> KUser::allUsers() {
QList<KUser> result;
@@ -257,7 +249,7 @@
d = new Private(getgrgid(KUser(mode).gid()));
}
-KUserGroup::KUserGroup(gid_t _gid)
+KUserGroup::KUserGroup(K_GID _gid)
: d(new Private(getgrgid(_gid)))
{
}
@@ -299,7 +291,7 @@
return gid() != gid_t(-1);
}
-gid_t KUserGroup::gid() const {
+K_GID KUserGroup::gid() const {
return d->gid;
}
Index: kuser.h
===================================================================
--- kuser.h (revision 715697)
+++ kuser.h (working copy)
@@ -23,15 +23,27 @@
#define KUSER_H
#include <kdecore_export.h>
-#include "ksharedptr.h"
-#include <sys/types.h>
+#include <ksharedptr.h>
+#include <QtCore/QVariant>
+
class KUserGroup;
class QString;
class QStringList;
-struct passwd;
template <class T> class QList;
+#ifdef Q_OS_WIN
+typedef void *K_UID;
+typedef void *K_GID;
+#else
+#include <sys/types.h>
+typedef uid_t K_UID;
+typedef gid_t K_GID;
+struct passwd;
+struct group;
+#endif
+
+
/**
* @short Represents a user on your system
*
@@ -71,7 +83,7 @@
* If the user does not exist isValid() will return false.
* @param uid the user id
*/
- explicit KUser(uid_t uid);
+ explicit KUser(K_UID uid);
/**
* Creates an object that contains information about the user with the given
@@ -89,6 +101,7 @@
*/
explicit KUser(const char* name);
+#ifndef Q_OS_WIN
/**
* Creates an object from a passwd structure.
* If the pointer is null isValid() will return false.
@@ -96,6 +109,7 @@
* @param p the passwd structure to create the user from
*/
explicit KUser(const passwd *p);
+#endif
/**
* Creates an object from another KUser object
@@ -133,13 +147,15 @@
* Returns the user id of the user.
* @return the id of the user or -1 if user is invalid
*/
- uid_t uid() const;
+ const K_UID uid() const;
+#ifndef Q_OS_WIN
/**
* Returns the group id of the user.
* @return the id of the group or -1 if user is invalid
*/
- gid_t gid() const;
+ const K_GID gid() const;
+#endif
/**
* Checks whether the user is the super user (root).
@@ -160,27 +176,6 @@
QString fullName() const;
/**
- * The user's room number.
- * @return the room number of the user or QString() if not set or the
- * user is invalid
- */
- QString roomNumber() const;
-
- /**
- * The user's work phone.
- * @return the work phone of the user or QString() if not set or the
- * user is invalid
- */
- QString workPhone() const;
-
- /**
- * The user's home phone.
- * @return the home phone of the user or QString() if not set or the
- * user is invalid
- */
- QString homePhone() const;
-
- /**
* The path to the user's home directory.
* @return the home directory of the user or QString() if the
* user is invalid
@@ -206,6 +201,15 @@
*/
QStringList groupNames() const;
+ /**
+ * Retruns an extended property or an invalid
+ * QVariant if the property is not set.
+ *
+ * currently supported properties: roomnumer, workphone and homephone
+ *
+ * \return a QVariant with value of the property
+ */
+ QVariant extendedProperty(const QByteArray &which) const ;
/**
* Destructor.
@@ -229,8 +233,6 @@
KSharedPtr<Private> d;
};
-struct group;
-
/**
* @short Represents a group on your system
*
@@ -246,6 +248,21 @@
public:
/**
+ * Create an object from a group name.
+ * If the group does not exist, isValid() will return false.
+ * @param name the name of the group
+ */
+ explicit KUserGroup(const QString& name);
+
+ /**
+ * Create an object from a group name.
+ * If the group does not exist, isValid() will return false.
+ * @param name the name of the group
+ */
+ explicit KUserGroup(const char *name);
+
+#ifndef Q_OS_WIN
+ /**
* Create an object from the group of the current user.
* @param mode if #KUser::UseEffectiveUID is passed the effective user
* will be used. If #KUser::UseRealUserID is passed the real user
@@ -262,28 +279,15 @@
* If the group does not exist, isValid() will return false.
* @param gid the group id
*/
- explicit KUserGroup(gid_t gid);
+ explicit KUserGroup(K_GID gid);
/**
- * Create an object from a group name.
- * If the group does not exist, isValid() will return false.
- * @param name the name of the group
- */
- explicit KUserGroup(const QString& name);
-
- /**
- * Create an object from a group name.
- * If the group does not exist, isValid() will return false.
- * @param name the name of the group
- */
- explicit KUserGroup(const char *name);
-
- /**
* Creates an object from a group structure.
* If the pointer is null, isValid() will return false.
* @param g the group structure to create the group from.
*/
explicit KUserGroup(const group *g);
+#endif
/**
* Creates a new KUserGroup instance from another KUserGroup object
@@ -320,11 +324,13 @@
*/
bool isValid() const;
+#ifndef Q_OS_WIN
/**
* Returns the group id of the group.
* @return the group id of the group or -1 if the group is invalid
*/
- gid_t gid() const;
+ K_GID gid() const;
+#endif
/**
* The name of the group.
Index: kuser_win.cpp
===================================================================
--- kuser_win.cpp (revision 0)
+++ kuser_win.cpp (revision 0)
@@ -0,0 +1,438 @@
+/*
+ * KUser - represent a user/account (Windows)
+ * Copyright (C) 2007 Bernhard Loos <nhuh.put@web.de>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include "kuser.h"
+
+#include <QtCore/QMutableStringListIterator>
+#include <QtCore/QDir>
+
+#include <windows.h>
+#include <lm.h>
+#include <Userenv.h>
+
+class KUser::Private : public KShared
+{
+ public:
+ PUSER_INFO_11 userInfo;
+ PSID sid;
+
+ Private() : userInfo(0), sid(0) {}
+
+ Private(PUSER_INFO_11 userInfo_, PSID sid_ = 0) : userInfo(userInfo_) {}
+
+ Private(const QString &name, PSID sid_ = 0) : userInfo(0), sid(0)
+ {
+ if (NetUserGetInfo(NULL, (LPCWSTR) name.utf16(), 11, (LPBYTE *) \
&userInfo) != NERR_Success) + goto error;
+
+ if (!sid_) {
+ DWORD size = 0;
+ SID_NAME_USE nameuse;
+ DWORD cchReferencedDomainName = 0;
+
+ if (!LookupAccountNameW(NULL, (LPCWSTR) name.utf16(), NULL, &size, \
NULL, &cchReferencedDomainName, &nameuse)) + goto error;
+ sid = (PSID) new BYTE[size];
+ if (!LookupAccountNameW(NULL, (LPCWSTR) name.utf16(), sid, &size, \
NULL, &cchReferencedDomainName, &nameuse)) + goto error;
+ }
+ else {
+ if (!IsValidSid(sid_))
+ goto error;
+
+ DWORD sidlength = GetLengthSid(sid_);
+ sid = (PSID) new BYTE[sidlength];
+ if (!CopySid(sidlength, sid, sid_))
+ goto error;
+ }
+
+ return;
+
+ error:
+ delete[] sid;
+ sid = 0;
+ if (userInfo) {
+ NetApiBufferFree(userInfo);
+ userInfo = 0;
+ }
+ }
+
+ ~Private()
+ {
+ if (userInfo)
+ NetApiBufferFree(userInfo);
+
+ delete[] sid;
+ }
+};
+
+KUser::KUser(UIDMode mode)
+ : d(0)
+{
+ Q_UNUSED(mode)
+
+ DWORD bufferLen = UNLEN + 1;
+ ushort buffer[UNLEN + 1];
+
+ if (GetUserNameW((LPWSTR) buffer, &bufferLen))
+ d = new Private(QString::fromUtf16(buffer));
+}
+
+KUser::KUser(K_UID uid)
+ : d(0)
+{
+ DWORD bufferLen = UNLEN + 1;
+ ushort buffer[UNLEN + 1];
+ SID_NAME_USE eUse;
+
+ if (LookupAccountSidW(NULL, uid, (LPWSTR) buffer, &bufferLen, NULL, NULL, \
&eUse)) + d = new Private(QString::fromUtf16(buffer), uid);
+}
+
+KUser::KUser(const QString &name)
+ : d(new Private(name))
+{
+}
+
+KUser::KUser(const char *name)
+ :d(new Private(QString::fromLocal8Bit(name)))
+{
+}
+
+KUser::KUser(const KUser &user)
+ : d(user.d)
+{
+}
+
+KUser &KUser::operator=(const KUser &user)
+{
+ d = user.d;
+ return *this;
+}
+
+bool KUser::operator==(const KUser &user) const
+{
+ if (!isValid() || !user.isValid())
+ return false;
+ return EqualSid(d->sid, user.d->sid);
+}
+
+bool KUser::operator !=(const KUser &user) const
+{
+ return !operator==(user);
+}
+
+bool KUser::isValid() const
+{
+ return d->userInfo != 0 && d->sid != 0;
+}
+
+bool KUser::isSuperUser() const
+{
+ return d->userInfo && d->userInfo->usri11_priv == USER_PRIV_ADMIN;
+}
+
+QString KUser::loginName() const
+{
+ return (d->userInfo ? QString::fromUtf16((ushort *) d->userInfo->usri11_name) : \
QString()); +}
+
+QString KUser::fullName() const
+{
+ return (d->userInfo ? QString::fromUtf16((ushort *) \
d->userInfo->usri11_full_name) : QString()); +}
+
+QString KUser::homeDir() const
+{
+ wchar_t profilesDir[MAX_PATH + 1] = { 0 };
+ DWORD Size = MAX_PATH+1;
+
+ if (d->userInfo == NULL || !GetProfilesDirectoryW(profilesDir, &Size)) {
+ return QString();
+ }
+
+ QDir dir = QDir::fromNativeSeparators(QString::fromUtf16((ushort *) \
profilesDir)); + return \
dir.absolutePath().append(QLatin1Char('/')).append(loginName()); +}
+
+QString KUser::shell() const
+{
+ return QString::fromAscii("cmd.exe");
+}
+
+QList<KUserGroup> KUser::groups() const
+{
+ QList<KUserGroup> result;
+
+ QStringList names(groupNames());
+
+ for (QStringList::const_iterator it = names.begin(); it != names.end(); ++it) {
+ result.append(KUserGroup(*it));
+ }
+
+ return result;
+}
+
+QStringList KUser::groupNames() const
+{
+ QStringList result;
+
+ if (!d->userInfo) {
+ return result;
+ }
+
+ PGROUP_USERS_INFO_0 pGroups = NULL;
+ DWORD dwEntriesRead = 0;
+ DWORD dwTotalEntries = 0;
+ NET_API_STATUS nStatus;
+
+ nStatus = NetUserGetGroups(NULL, d->userInfo->usri11_name, 0, (LPBYTE *) \
&pGroups, MAX_PREFERRED_LENGTH, &dwEntriesRead, &dwTotalEntries); +
+ if (nStatus == NERR_Success) {
+ for (DWORD i = 0; i < dwEntriesRead; ++i) {
+ result.append(QString::fromUtf16((ushort *) pGroups[i].grui0_name));
+ }
+ }
+
+ if (pGroups) {
+ NetApiBufferFree(pGroups);
+ }
+
+ return result;
+}
+
+const K_UID KUser::uid() const
+{
+ return d->sid;
+}
+
+QVariant KUser::extendedProperty(const QByteArray &which) const
+{
+ return QVariant();
+}
+
+QList<KUser> KUser::allUsers()
+{
+ QList<KUser> result;
+
+ NET_API_STATUS nStatus;
+ PUSER_INFO_11 pUser = NULL;
+ DWORD dwEntriesRead = 0;
+ DWORD dwTotalEntries = 0;
+ DWORD dwResumeHandle = 0;
+
+ KUser tmp;
+
+ do {
+ nStatus = NetUserEnum(NULL, 11, 0, (LPBYTE*) &pUser, 1, &dwEntriesRead, \
&dwTotalEntries, &dwResumeHandle); +
+ if ((nStatus == NERR_Success || nStatus == ERROR_MORE_DATA) && dwEntriesRead \
> 0) { + tmp.d = new Private(pUser);
+ result.append(tmp);
+ }
+ } while (nStatus == ERROR_MORE_DATA);
+
+ return result;
+}
+
+QStringList KUser::allUserNames()
+{
+ QStringList result;
+
+ NET_API_STATUS nStatus;
+ PUSER_INFO_0 pUsers = NULL;
+ DWORD dwEntriesRead = 0;
+ DWORD dwTotalEntries = 0;
+
+ nStatus = NetUserEnum(NULL, 0, 0, (LPBYTE*) &pUsers, MAX_PREFERRED_LENGTH, \
&dwEntriesRead, &dwTotalEntries, NULL); +
+ if (nStatus == NERR_Success) {
+ for (DWORD i = 0; i < dwEntriesRead; ++i) {
+ result.append(QString::fromUtf16((ushort *) pUsers[i].usri0_name));
+ }
+ }
+
+ if (pUsers) {
+ NetApiBufferFree(pUsers);
+ }
+
+ return result;
+}
+
+KUser::~KUser()
+{
+}
+
+class KUserGroup::Private : public KShared
+{
+ public:
+ PGROUP_INFO_0 groupInfo;
+
+ Private() : groupInfo(NULL) {}
+ Private(PGROUP_INFO_0 groupInfo_) : groupInfo(groupInfo_) {}
+ Private(const QString &Name) : groupInfo(NULL)
+ {
+ NetGroupGetInfo(NULL, (PCWSTR) Name.utf16(), 0, (PBYTE *) &groupInfo);
+ }
+
+ ~Private()
+ {
+ if (groupInfo) {
+ NetApiBufferFree(groupInfo);
+ }
+ }
+};
+
+KUserGroup::KUserGroup(const QString &_name)
+ : d(new Private(_name))
+{
+}
+
+KUserGroup::KUserGroup(const char *_name)
+ : d(new Private(QString(_name)))
+{
+}
+
+KUserGroup::KUserGroup(const KUserGroup &group)
+ : d(group.d)
+{
+}
+
+KUserGroup& KUserGroup::operator =(const KUserGroup &group)
+{
+ d = group.d;
+ return *this;
+}
+
+bool KUserGroup::operator==(const KUserGroup &group) const
+{
+ if (d->groupInfo == NULL || group.d->groupInfo == NULL) {
+ return false;
+ }
+ return wcscmp(d->groupInfo->grpi0_name, group.d->groupInfo->grpi0_name) == 0;
+}
+
+bool KUserGroup::operator!=(const KUserGroup &group) const
+{
+ return !operator==(group);
+}
+
+bool KUserGroup::isValid() const
+{
+ return d->groupInfo != NULL;
+}
+
+QString KUserGroup::name() const
+{
+ return QString::fromUtf16((ushort *) d->groupInfo->grpi0_name);
+}
+
+QList<KUser> KUserGroup::users() const
+{
+ QList<KUser> Result;
+
+ QStringList Names(userNames());
+
+ for (QStringList::const_iterator it = Names.begin(); it != Names.end(); ++it) {
+ Result.append(KUser(*it));
+ }
+
+ return Result;
+}
+
+QStringList KUserGroup::userNames() const
+{
+ QStringList result;
+
+ if (!d->groupInfo) {
+ return result;
+ }
+
+ PGROUP_USERS_INFO_0 pUsers = NULL;
+ DWORD dwEntriesRead = 0;
+ DWORD dwTotalEntries = 0;
+ NET_API_STATUS nStatus;
+
+ nStatus = NetGroupGetUsers(NULL, d->groupInfo->grpi0_name, 0, (LPBYTE *) \
&pUsers, MAX_PREFERRED_LENGTH, &dwEntriesRead, &dwTotalEntries, NULL); +
+ if (nStatus == NERR_Success) {
+ for (DWORD i = 0; i < dwEntriesRead; ++i) {
+ result.append(QString::fromUtf16((ushort *) pUsers[i].grui0_name));
+ }
+ }
+
+ if (pUsers) {
+ NetApiBufferFree(pUsers);
+ }
+
+ return result;
+}
+
+QList<KUserGroup> KUserGroup::allGroups()
+{
+ QList<KUserGroup> result;
+
+ NET_API_STATUS nStatus;
+ PGROUP_INFO_0 pGroup=NULL;
+ DWORD dwEntriesRead=0;
+ DWORD dwTotalEntries=0;
+ DWORD dwResumeHandle=0;
+
+ KUserGroup tmp("");
+
+ do {
+ nStatus = NetGroupEnum(NULL, 0, (LPBYTE*) &pGroup, 1, &dwEntriesRead, \
&dwTotalEntries, &dwResumeHandle); +
+ if ((nStatus == NERR_Success || nStatus == ERROR_MORE_DATA) && dwEntriesRead \
> 0) { + tmp.d = new Private(pGroup);
+ result.append(tmp);
+ }
+ } while (nStatus == ERROR_MORE_DATA);
+
+ return result;
+}
+
+QStringList KUserGroup::allGroupNames()
+{
+ QStringList result;
+
+ NET_API_STATUS nStatus;
+ PGROUP_INFO_0 pGroups=NULL;
+ DWORD dwEntriesRead=0;
+ DWORD dwTotalEntries=0;
+
+ nStatus = NetGroupEnum(NULL, 0, (LPBYTE*) &pGroups, MAX_PREFERRED_LENGTH, \
&dwEntriesRead, &dwTotalEntries, NULL); +
+ if (nStatus == NERR_Success) {
+ for (DWORD i = 0; i < dwEntriesRead; ++i) {
+ result.append(QString::fromUtf16((ushort *) pGroups[i].grpi0_name));
+ }
+ }
+
+ if (pGroups) {
+ NetApiBufferFree(pGroups);
+ }
+
+ return result;
+}
+
+KUserGroup::~KUserGroup()
+{
+}
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic