LinuxDevCenter.com

oreilly.comSafari Books Online.Conferences.

We've expanded our Linux news coverage and improved our search! Search for all things Linux across O'Reilly!

Search
Search Tips

advertisement

Listen Print Subscribe to Linux Subscribe to Newsletters

Writing PAM-Capable Applications, Part One
Pages: 1, 2, 3

Writing your own conversation function

The conversation structure itself is actually:
struct pam_conv {
    int (*conv)(int num_msg,
        const struct pam_message **msg,
        struct pam_response **resp,
        void *appdata_ptr);
    void *appdata_ptr;
};

When a module calls this function, the appdata_ptr is passed as the parameter of the same name.



The msg parameter is an array of pointers to message structures (pam_message). The message structures are provided by the module and contain the messages the module expects the application to present to the user. The num_msg parameter contains the length of the array.

The module provides a pointer in the resp parameter, which it expects the function to fill with an array of pam_response structures. The application should provide the response to each message (if any) in the corresponding element of the response array. This array will be freed with the free() function and should be allocated with one of the malloc() family of functions.

In C++ this looks like:

reply = 
  static_cast<pam_response*>(std::calloc(num_msg, sizeof(pam_response)));
 if(!reply)
	 return PAM_SYSTEM_ERROR;
struct pam_message {
    int msg_style;
    const char *msg;
};

struct pam_response {
    char *resp;
    int resp_retcode;
};


/*
 * DEMONSTRATION CODE ONLY
 * This WILL NOT work as-is.
 */

// The 'extern C' tells the compiler to generate the function 
// so it can be called by C code.
extern "C" int Conversation(int num_msg, const pam_message **msg,
           pam_response **resp, void *appdata_ptr)
{
#if WE_USE_APPDATA
  myApplicationData *data = 
    static_cast<myApplicationData*>(appdata_ptr);

  if (!data)
	  return PAM_SYSTEM_ERR;
#endif

  if (num_msg <= 0)
	  return PAM_CONV_ERR;

  pam_response* reply = 
    static_cast<pam_response*>(std::calloc(num_msg, sizeof(pam_response)));
  if (!reply)
	  return PAM_SYSTEM_ERR;

  for (int replies = 0; replies < num_msg; replies++) {

    switch (msg[replies]->msg_style) {
      case PAM_PROMPT_ECHO_OFF: { // Don't echo sensitive data
				// Turn echoing off (code not included)

				// output the message from the PAM module
        if(msg[replies]->msg)
					std::cout << msg[replies]->msg;

				// Get some sort of input from the user
				std::string data=get_input();
        reply[replies].resp_retcode = PAM_SUCCESS;
        reply[replies].resp = std::strdup(data.c_str());
        break; }

      case PAM_PROMPT_ECHO_ON: { // Okay to echo
				// Make sure we're echoing output
                                // (code not included)
				// Do the same as for ECHO_OFF
				}

      default: // Say, what?
        std::free(reply);	// Don't leak
        return PAM_CONV_ERR;
    }
  }

  *resp = reply;

  return PAM_SUCCESS;
}

The memory for the response structure must be dynamically allocated and is freed within the module. A note for C++ users: Since PAM is a C-based library, malloc() must be used for the allocation, rather than new.

There is currently only one response code in the response structure: 0, and it doesn't yet mean anything. The response code is in the structure for future expansion of the Linux-PAM system. There are, however, four possible message styles:

  • PAM_PROMPT_ECHO_OFF
  • PAM_PROMPT_ECHO_ON
  • PAM_ERROR_MSG
  • PAM_TEXT_INFO

Note that PAM_MAX_MSG_SIZE is NOT currently enforced by Linux-PAM and should be enforced by applications (for security).

Pages: 1, 2, 3

Next Pagearrow




Tagged Articles

Be the first to post this article to del.icio.us

Sponsored Resources

  • Inside Lightroom
Advertisement

Sponsored by:

O'Reilly Media

©2009, O'Reilly Media, Inc.
(707) 827-7000 / (800) 998-9938
All trademarks and registered trademarks appearing on oreilly.com are the property of their respective owners.
About O'Reilly
Academic Solutions
Authors
Contacts
Customer Service
Jobs
Newsletters
O'Reilly Labs
Press Room
Privacy Policy
RSS Feeds
Terms of Service
User Groups
Writing for O'Reilly
Content Archive
Business Technology
Computer Technology
Google
Microsoft
Mobile
Network
Operating System
Digital Photography
Programming
Software
Web
Web Design
More O'Reilly Sites
O'Reilly Radar
Ignite
Tools of Change for Publishing
Digital Media
Inside iPhone
O'Reilly FYI
makezine.com
craftzine.com
hackszine.com
perl.com
xml.com

Partner Sites
InsideRIA
java.net
O'Reilly Insights on Forbes.com