+ if (!is_bopen(bfd)) {
+ Dmsg0(000, "===== BFD is not open!!!!\n");
+ }
+ Dsm_check(999);
+ return CF_EXTRACT;
+}
+
+/**
+ * Reset the file attributes after all file I/O is done -- this allows
+ * the previous access time/dates to be set properly, and it also allows
+ * us to properly set directory permissions.
+ * Not currently Implemented.
+ */
+bool plugin_set_attributes(JCR *jcr, ATTR *attr, BFILE *ofd)
+{
+ Plugin *plugin = (Plugin *)jcr->plugin;
+ struct restore_pkt rp;
+
+ Dmsg0(dbglvl, "plugin_set_attributes\n");
+
+ if (!plugin || !jcr->plugin_ctx) {
+ return false;
+ }
+
+ memset(&rp, 0, sizeof(rp));
+ rp.pkt_size = sizeof(rp);
+ rp.pkt_end = sizeof(rp);
+ rp.stream = attr->stream;
+ rp.data_stream = attr->data_stream;
+ rp.type = attr->type;
+ rp.file_index = attr->file_index;
+ rp.LinkFI = attr->LinkFI;
+ rp.uid = attr->uid;
+ rp.statp = attr->statp; /* structure assignment */
+ rp.attrEx = attr->attrEx;
+ rp.ofname = attr->ofname;
+ rp.olname = attr->olname;
+ rp.where = jcr->where;
+ rp.RegexWhere = jcr->RegexWhere;
+ rp.replace = jcr->replace;
+ rp.create_status = CF_ERROR;
+
+ plug_func(plugin)->setFileAttributes(jcr->plugin_ctx, &rp);
+
+ if (rp.create_status == CF_CORE) {
+ set_attributes(jcr, attr, ofd);
+ } else {
+ if (is_bopen(ofd)) {
+ bclose(ofd);
+ }
+ pm_strcpy(attr->ofname, "*none*");
+ }
+
+ Dsm_check(999);
+ return true;
+}
+
+/*
+ * The Plugin ACL data backup. We are using a new Plugin callback:
+ * handleXACLdata() for that. The new callback get a pointer to
+ * struct xacl_pkt as a main argument which consist of the following
+ * data:
+ * xacl.func - could be the one of BACL_BACKUP, BACL_RESTORE,
+ * BXATTR_BACKUP, BXATTR_RESTORE
+ * xacl.count - the length of data at the content buffer
+ * xacl.content - the buffer itself
+ * The buffer (xacl.content) is supplied by Bacula during restore and has to
+ * be supplied by a Plugin during backup.
+ * The new callback should return bRC_OK on success and bRC_Error on
+ * any error.
+ *
+ * in:
+ * jcr - Job Control Record
+ * ff_pkt - file save packet
+ * data is a pointer to variable returned
+ * out:
+ * data - the pointer to data buffer returned from plugin
+ * 0 - Success, no more data to save
+ * > 0 - Success and the number of bytes returned in **data buffer
+ * -1 - Error, no acls data to backup
+ */
+int plugin_backup_acl(JCR *jcr, FF_PKT *ff_pkt, char **data)
+{
+ struct xacl_pkt xacl;
+ Plugin *plugin = (Plugin *)jcr->plugin;
+ bRC rc;
+
+ Dmsg0(dbglvl, "plugin_backup_acl\n");
+
+ /* check of input variables */
+ if (!plugin || !jcr->plugin_ctx || !data) {
+ return 0;
+ }
+
+ /* prepare the xacl packet */
+ memset(&xacl, 0, sizeof(xacl));
+ xacl.pkt_size = sizeof(xacl);
+ xacl.pkt_end = sizeof(xacl);
+ xacl.func = BACL_BACKUP;
+
+ rc = plug_func(plugin)->handleXACLdata(jcr->plugin_ctx, &xacl);
+
+ /* check out status */
+ if (rc != bRC_OK){
+ Dmsg0(dbglvl, "plugin->handleXACLdata returned error\n");
+ return -1;
+ }
+ if (xacl.count > 0){
+ /* we have something to save, so prepare return data */
+ *data = xacl.content;
+ return xacl.count;
+ }
+
+ return 0;
+}
+
+/*
+ * Called here when Bacula got ACL stream to restore but not every stream but
+ * a specific one: STREAM_XACL_PLUGIN_ACL which means a plugin has to
+ * be called.
+ *
+ * in:
+ * jcr - Job Control Record
+ * data - content to restore
+ * length - the length of the content to restore
+ * out:
+ * true - when successful
+ * false - on any Error
+ */
+bool plugin_restore_acl(JCR *jcr, char *data, uint32_t length)
+{
+ struct xacl_pkt xacl;
+ Plugin *plugin = (Plugin *)jcr->plugin;
+ bRC rc;
+
+ Dmsg0(dbglvl, "plugin_restore_acl\n");
+
+ /* check of input variables */
+ if (!plugin || !jcr->plugin_ctx || !data || length == 0) {
+ return true;
+ }
+
+ /* prepare the xacl packet */
+ memset(&xacl, 0, sizeof(xacl));
+ xacl.pkt_size = sizeof(xacl);
+ xacl.pkt_end = sizeof(xacl);
+ xacl.func = BACL_RESTORE;
+ xacl.content = data;
+ xacl.count = length;
+
+ rc = plug_func(plugin)->handleXACLdata(jcr->plugin_ctx, &xacl);
+
+ /* check out status */
+ if (rc != bRC_OK){
+ Dmsg0(dbglvl, "plugin->handleXACLdata returned error\n");
+ return false;
+ }
+
+ return true;
+}
+
+/*
+ * The Plugin XATTR data backup. We are using a new Plugin callback:
+ * handleXACLdata() for that. Check plugin_backup_acl for new callback
+ * description.
+ *
+ * in:
+ * jcr - Job Control Record
+ * ff_pkt - file save packet
+ * data is a pointer to variable returned
+ * out:
+ * data - the pointer to data buffer returned from plugin
+ * 0 - Success, no more data to save
+ * >0 - Success and the number of bytes returned in **data buffer
+ * <0 - Error
+ */
+int plugin_backup_xattr(JCR *jcr, FF_PKT *ff_pkt, char **data)
+{
+
+ struct xacl_pkt xacl;
+ Plugin *plugin = (Plugin *)jcr->plugin;
+ bRC rc;
+
+ Dmsg0(dbglvl, "plugin_backup_xattr\n");
+
+ /* check of input variables */
+ if (!plugin || !jcr->plugin_ctx || !data) {
+ return 0;
+ }
+
+ /* prepare the xacl packet */
+ memset(&xacl, 0, sizeof(xacl));
+ xacl.pkt_size = sizeof(xacl);
+ xacl.pkt_end = sizeof(xacl);
+ xacl.func = BXATTR_BACKUP;
+
+ rc = plug_func(plugin)->handleXACLdata(jcr->plugin_ctx, &xacl);
+
+ /* check out status */
+ if (rc != bRC_OK){
+ Dmsg0(dbglvl, "plugin->handleXACLdata returned error\n");
+ return -1;