1 /*
2  * Copyright (C) 2018-2020 Alexandros Theodotou <alex at zrythm dot org>
3  *
4  * This file is part of Zrythm
5  *
6  * Zrythm is free software: you can redistribute it and/or modify
7  * it under the terms of the GNU Affero General Public License as published by
8  * the Free Software Foundation, either version 3 of the License, or
9  * (at your option) any later version.
10  *
11  * Zrythm is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU Affero General Public License for more details.
15  *
16  * You should have received a copy of the GNU Affero General Public License
17  * along with Zrythm.  If not, see <https://www.gnu.org/licenses/>.
18  */
19 
20 /**
21  * \file
22  *
23  * Plugin manager.
24  */
25 
26 #ifndef __PLUGINS_PLUGIN_MANAGER_H__
27 #define __PLUGINS_PLUGIN_MANAGER_H__
28 
29 #include "plugins/lv2/lv2_urid.h"
30 #include "plugins/plugin_descriptor.h"
31 #include "utils/symap.h"
32 
33 #include "zix/sem.h"
34 
35 #include <lilv/lilv.h>
36 
37 typedef struct CachedPluginDescriptors
38   CachedPluginDescriptors;
39 typedef struct PluginCollections PluginCollections;
40 
41 /**
42  * @addtogroup plugins
43  *
44  * @{
45  */
46 
47 #define PLUGIN_MANAGER (ZRYTHM->plugin_manager)
48 #define LILV_WORLD (PLUGIN_MANAGER->lilv_world)
49 #define LILV_PLUGINS (PLUGIN_MANAGER->lilv_plugins)
50 #define LV2_GENERATOR_PLUGIN "Generator"
51 #define LV2_CONSTANT_PLUGIN "Constant"
52 #define LV2_INSTRUMENT_PLUGIN "Instrument"
53 #define LV2_OSCILLATOR_PLUGIN "Oscillator"
54 #define PM_URIDS (PLUGIN_MANAGER->urids)
55 #define PM_SYMAP (PLUGIN_MANAGER->symap)
56 #define PM_SYMAP_LOCK (PLUGIN_MANAGER->symap_lock)
57 #define PM_GET_NODE(uri) \
58   plugin_manager_get_node (PLUGIN_MANAGER, uri)
59 
60 typedef struct PluginDescriptor PluginDescriptor;
61 
62 /**
63  * The PluginManager is responsible for scanning
64  * and keeping track of available Plugin's.
65  */
66 typedef struct PluginManager
67 {
68   /**
69    * Scanned plugin descriptors.
70    */
71   GPtrArray *         plugin_descriptors;
72 
73   /** Plugin categories. */
74   char *              plugin_categories[500];
75   int                 num_plugin_categories;
76 
77   /** Plugin authors. */
78   char *              plugin_authors[6000];
79   int                 num_plugin_authors;
80 
81   LilvWorld *         lilv_world;
82   const LilvPlugins * lilv_plugins;
83 
84   LilvNode **         nodes;
85   int                 num_nodes;
86   size_t              nodes_size;
87 
88   /** Cached VST descriptors */
89   CachedPluginDescriptors * cached_plugin_descriptors;
90 
91   /** Plugin collections. */
92   PluginCollections *    collections;
93 
94   /** URI map for URID feature. */
95   Symap*                 symap;
96   /** Lock for URI map. */
97   ZixSem                 symap_lock;
98 
99   /** URIDs. */
100   Lv2URIDs               urids;
101 
102   char *                 lv2_path;
103 
104   /** Whether the plugin manager has been set up
105    * already. */
106   bool                   setup;
107 
108 } PluginManager;
109 
110 PluginManager *
111 plugin_manager_new (void);
112 
113 /**
114  * Returns a cached LilvNode for the given URI.
115  *
116  * If a node doesn't exist for the given URI, a
117  * node is created and cached.
118  */
119 const LilvNode *
120 plugin_manager_get_node (
121   PluginManager * self,
122   const char *    uri);
123 
124 /**
125  * Scans for plugins, optionally updating the
126  * progress.
127  *
128  * @param max_progress Maximum progress for this
129  *   stage.
130  * @param progress Pointer to a double (0.0-1.0) to
131  *   update based on the current progress.
132  */
133 void
134 plugin_manager_scan_plugins (
135   PluginManager * self,
136   const double    max_progress,
137   double *        progress);
138 
139 /**
140  * Returns the PluginDescriptor instance for the
141  * given URI.
142  *
143  * This instance is held by the plugin manager and
144  * must not be free'd.
145  */
146 PluginDescriptor *
147 plugin_manager_find_plugin_from_uri (
148   PluginManager * self,
149   const char *    uri);
150 
151 /**
152  * Finds and returns the PluginDescriptor instance
153  * matching the given descriptor.
154  *
155  * This instance is held by the plugin manager and
156  * must not be free'd.
157  */
158 PluginDescriptor *
159 plugin_manager_find_from_descriptor (
160   PluginManager *          self,
161   const PluginDescriptor * src_descr);
162 
163 /**
164  * Returns if the plugin manager supports the given
165  * plugin protocol.
166  */
167 bool
168 plugin_manager_supports_protocol (
169   PluginManager * self,
170   PluginProtocol  protocol);
171 
172 /**
173  * Returns an instrument plugin, if any.
174  */
175 PluginDescriptor *
176 plugin_manager_pick_instrument (
177   PluginManager * self);
178 
179 void
180 plugin_manager_clear_plugins (
181   PluginManager * self);
182 
183 void
184 plugin_manager_free (
185   PluginManager * self);
186 
187 /**
188  * @}
189  */
190 
191 #endif
192