EXPORTED int mailbox_user_flag(struct mailbox *mailbox, const char *flag,
                      int *flagnum, int create)
{
    int userflag;
    int emptyflag = -1;

    for (userflag = 0; userflag < MAX_USER_FLAGS; userflag++) {
        // keep track of the first empty slot
        if (!mailbox->h.flagname[userflag]) {
            if (emptyflag == -1)
                emptyflag = userflag;
            continue;
        }

        // name matches?  We've found the flag
        if (!strcasecmp(flag, mailbox->h.flagname[userflag]))
            break;
    }

    if (userflag == MAX_USER_FLAGS) {
        if (!create)
            return IMAP_NOTFOUND;

        if (emptyflag == -1)
            return IMAP_USERFLAG_EXHAUSTED;

        /* stop imapd exhausting flags */
        if (create == 1 && _too_many_flags(flag, emptyflag)) {
            xsyslog(LOG_ERR, "IOERROR: out of flags",
                             "mailbox=<%s> flag=<%s>",
                             mailbox_name(mailbox), flag);
            return IMAP_USERFLAG_EXHAUSTED;
        }

        /* need to be index locked to make flag changes */
        if (!mailbox_index_islocked(mailbox, 1))
            return IMAP_MAILBOX_LOCKED;

        if (!imparse_isatom(flag))
            return IMAP_INVALID_IDENTIFIER;

        /* set the flag and mark the header dirty */
        userflag = emptyflag;
        mailbox->h.flagname[emptyflag] = xstrdup(flag);
        mailbox->header_dirty = 1;
    }

    if (flagnum) *flagnum = userflag;

    return 0;
}
EXPORTED int mailbox_user_flag(struct mailbox *mailbox, const char *flag,
                      int *flagnum, int create)
{
    int userflag;
    int emptyflag = -1;

    for (userflag = 0; userflag < MAX_USER_FLAGS; userflag++) {
         
        if (!mailbox->h.flagname[userflag]) {
            if (emptyflag == -1)
                emptyflag = userflag;
            continue;
        }

         
        if (!strcasecmp(flag, mailbox->h.flagname[userflag]))
            break;
    }

    if (userflag == MAX_USER_FLAGS) {
        if (!create)
            return IMAP_NOTFOUND;

        if (emptyflag == -1)
            return IMAP_USERFLAG_EXHAUSTED;

         
        if (create == 1 && _too_many_flags(flag, emptyflag)) {
            xsyslog(LOG_ERR, "IOERROR: out of flags",
                             "mailbox=<%s> flag=<%s>",
                             mailbox_name(mailbox), flag);
            return IMAP_USERFLAG_EXHAUSTED;
        }

         
        if (!mailbox_index_islocked(mailbox, 1))
            return IMAP_MAILBOX_LOCKED;

        if (!imparse_isatom(flag))
            return IMAP_INVALID_IDENTIFIER;

         
        userflag = emptyflag;
        mailbox->h.flagname[emptyflag] = xstrdup(flag);
        mailbox->header_dirty = 1;
    }

    if (flagnum) *flagnum = userflag;

    return 0;
}