KiCad PCB EDA Suite
io_mgr.cpp
Go to the documentation of this file.
1/*
2 * This program source code file is part of KiCad, a free EDA CAD application.
3 *
4 * Copyright (C) 2011-2012 SoftPLC Corporation, Dick Hollenbeck <[email protected]>
5 * Copyright (C) 2016-2021 KiCad Developers, see AUTHORS.txt for contributors.
6 *
7 * This program is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation; either version 2
10 * of the License, or (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, you may find one here:
19 * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
20 * or you may search the http://www.gnu.org website for the version 2 license,
21 * or you may write to the Free Software Foundation, Inc.,
22 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
23 */
24
25#include <wx/filename.h>
26#include <wx/uri.h>
27
28#include <config.h>
31#include <io_mgr.h>
41
42#define FMT_UNIMPLEMENTED _( "Plugin \"%s\" does not implement the \"%s\" function." )
43#define FMT_NOTFOUND _( "Plugin type \"%s\" is not found." )
44
45
46// Some day plugins might be in separate DLL/DSOs, simply because of numbers of them
47// and code size. Until then, use the simplest method:
48
49// This implementation is one of two which could be done.
50// The other one would cater to DLL/DSO's. But since it would be nearly
51// impossible to link a KICAD type DLL/DSO right now without pulling in all
52// ::Draw() functions, I forgo that option temporarily.
53
54// Some day it may be possible to have some built in AND some DLL/DSO
55// plugins coexisting.
56
57
59{
60 // This implementation is subject to change, any magic is allowed here.
61 // The public IO_MGR API is the only pertinent public information.
62
63 return PLUGIN_REGISTRY::Instance()->Create( aFileType );
64}
65
66
68{
69 // This function is a place holder for a future point in time where
70 // the plugin is a DLL/DSO. It could do reference counting, and then
71 // unload the DLL/DSO when count goes to zero.
72
73 delete aPlugin;
74}
75
76
77const wxString IO_MGR::ShowType( PCB_FILE_T aType )
78{
79 const auto& plugins = PLUGIN_REGISTRY::Instance()->AllPlugins();
80
81 for( const auto& plugin : plugins )
82 {
83 if ( plugin.m_type == aType )
84 {
85 return plugin.m_name;
86 }
87 }
88
89 return wxString::Format( _( "UNKNOWN (%d)" ), aType );
90}
91
92
94{
95 const auto& plugins = PLUGIN_REGISTRY::Instance()->AllPlugins();
96
97 for( const auto& plugin : plugins )
98 {
99 if ( plugin.m_name == aType )
100 {
101 return plugin.m_type;
102 }
103 }
104
105 return PCB_FILE_T( -1 );
106}
107
108
109const wxString IO_MGR::GetFileExtension( PCB_FILE_T aFileType )
110{
111 wxString ext = wxEmptyString;
112 PLUGIN* plugin = PluginFind( aFileType );
113
114 if( plugin != nullptr )
115 {
116 ext = plugin->GetFileExtension();
117 PluginRelease( plugin );
118 }
119
120 return ext;
121}
122
123
125{
126 PCB_FILE_T ret = KICAD_SEXP; // default guess, unless detected otherwise.
127 wxFileName fn( aLibPath );
128
129 if( fn.GetExt() == LegacyFootprintLibPathExtension )
130 {
131 ret = LEGACY;
132 }
133 else if( fn.GetExt() == GedaPcbFootprintLibFileExtension )
134 {
135 ret = GEDA_PCB;
136 }
137 else if( fn.GetExt() == EagleFootprintLibPathExtension )
138 {
139 ret = EAGLE;
140 }
141 else if( fn.GetExt() == AltiumFootprintLibPathExtension )
142 {
143 ret = ALTIUM_DESIGNER;
144 }
145
146 // Test this one anyways, even though it's the default guess, to avoid
147 // the wxURI instantiation below.
148 // We default ret to KICAD above, because somebody might have
149 // mistakenly put a pretty library into a directory other than
150 // *.pretty/ with *.kicad_mod in there., and I don't want to return -1,
151 // since we only claimed to be guessing.
152 //
153 else if( fn.GetExt() == KiCadFootprintLibPathExtension )
154 {
155 ret = KICAD_SEXP;
156 }
157
158 return ret;
159}
160
161
162BOARD* IO_MGR::Load( PCB_FILE_T aFileType, const wxString& aFileName, BOARD* aAppendToMe,
163 const STRING_UTF8_MAP* aProperties, PROJECT* aProject,
164 PROGRESS_REPORTER* aProgressReporter )
165{
166 // release the PLUGIN even if an exception is thrown.
167 PLUGIN::RELEASER pi( PluginFind( aFileType ) );
168
169 if( (PLUGIN*) pi ) // test pi->plugin
170 {
171 return pi->Load( aFileName, aAppendToMe, aProperties, aProject, aProgressReporter );
172 }
173
174 THROW_IO_ERROR( wxString::Format( FMT_NOTFOUND, ShowType( aFileType ).GetData() ) );
175}
176
177
178void IO_MGR::Save( PCB_FILE_T aFileType, const wxString& aFileName, BOARD* aBoard,
179 const STRING_UTF8_MAP* aProperties )
180{
181 // release the PLUGIN even if an exception is thrown.
182 PLUGIN::RELEASER pi( PluginFind( aFileType ) );
183
184 if( (PLUGIN*) pi ) // test pi->plugin
185 {
186 pi->Save( aFileName, aBoard, aProperties ); // virtual
187 return;
188 }
189
190 THROW_IO_ERROR( wxString::Format( FMT_NOTFOUND, ShowType( aFileType ).GetData() ) );
191}
192
193// These text strings are "truth" for identifying the plugins. If you change the spellings,
194// you will obsolete library tables, so don't do it. Additions are OK.
196 []() -> PLUGIN* { return new EAGLE_PLUGIN; } );
198 wxT("KiCad"), []() -> PLUGIN* { return new PCB_PLUGIN; } );
200 []() -> PLUGIN* { return new PCAD_PLUGIN; } );
202 []() -> PLUGIN* { return new FABMASTER_PLUGIN; } );
204 wxT( "Altium Designer" ), []() -> PLUGIN* { return new ALTIUM_DESIGNER_PLUGIN; } );
206 wxT( "Altium Circuit Studio" ),
207 []() -> PLUGIN* { return new ALTIUM_CIRCUIT_STUDIO_PLUGIN; } );
209 wxT( "Altium Circuit Maker" ),
210 []() -> PLUGIN* { return new ALTIUM_CIRCUIT_MAKER_PLUGIN; } );
212 wxT( "CADSTAR PCB Archive" ), []() -> PLUGIN* { return new CADSTAR_PCB_ARCHIVE_PLUGIN; } );
214 []() -> PLUGIN* { return new LEGACY_PLUGIN; } );
216 []() -> PLUGIN* { return new GPCB_PLUGIN; } );
Pcbnew PLUGIN for CADSTAR PCB Archive (*.cpa) format: an ASCII format based on S-expressions.
Information pertinent to a Pcbnew printed circuit board.
Definition: board.h:265
Works with Eagle 6.x XML board files and footprints to implement the Pcbnew PLUGIN API or a portion o...
Definition: eagle_plugin.h:130
A PLUGIN derivation for saving and loading Geda PCB files.
Definition: gpcb_plugin.h:47
PLUGIN * Create(PCB_FILE_T aFileType) const
Definition: io_mgr.h:107
const std::vector< ENTRY > & AllPlugins() const
Definition: io_mgr.h:120
static PLUGIN_REGISTRY * Instance()
Definition: io_mgr.h:86
static const wxString ShowType(PCB_FILE_T aFileType)
Return a brief name for a plugin given aFileType enum.
Definition: io_mgr.cpp:77
static void PluginRelease(PLUGIN *aPlugin)
Release a PLUGIN back to the system and may cause it to be unloaded from memory.
Definition: io_mgr.cpp:67
static const wxString GetFileExtension(PCB_FILE_T aFileType)
Return the file extension for aFileType.
Definition: io_mgr.cpp:109
static PCB_FILE_T GuessPluginTypeFromLibPath(const wxString &aLibPath)
Return a plugin type given a footprint library's libPath.
Definition: io_mgr.cpp:124
PCB_FILE_T
The set of file types that the IO_MGR knows about, and for which there has been a plugin written.
Definition: io_mgr.h:54
@ LEGACY
Legacy Pcbnew file formats prior to s-expression.
Definition: io_mgr.h:55
@ ALTIUM_DESIGNER
Definition: io_mgr.h:60
@ KICAD_SEXP
S-expression Pcbnew file format.
Definition: io_mgr.h:56
@ ALTIUM_CIRCUIT_MAKER
Definition: io_mgr.h:62
@ PCAD
Definition: io_mgr.h:58
@ EAGLE
Definition: io_mgr.h:57
@ CADSTAR_PCB_ARCHIVE
Definition: io_mgr.h:63
@ GEDA_PCB
Geda PCB file formats.
Definition: io_mgr.h:64
@ FABMASTER
Definition: io_mgr.h:59
@ ALTIUM_CIRCUIT_STUDIO
Definition: io_mgr.h:61
static PCB_FILE_T EnumFromStr(const wxString &aFileType)
Return the PCB_FILE_T from the corresponding plugin type name: "kicad", "legacy", etc.
Definition: io_mgr.cpp:93
static BOARD * Load(PCB_FILE_T aFileType, const wxString &aFileName, BOARD *aAppendToMe=nullptr, const STRING_UTF8_MAP *aProperties=nullptr, PROJECT *aProject=nullptr, PROGRESS_REPORTER *aProgressReporter=nullptr)
Find the requested PLUGIN and if found, calls the PLUGIN::Load() function on it using the arguments p...
Definition: io_mgr.cpp:162
static PLUGIN * PluginFind(PCB_FILE_T aFileType)
Return a PLUGIN which the caller can use to import, export, save, or load design documents.
Definition: io_mgr.cpp:58
static void Save(PCB_FILE_T aFileType, const wxString &aFileName, BOARD *aBoard, const STRING_UTF8_MAP *aProperties=nullptr)
Write either a full aBoard to a storage file in a format that this implementation knows about,...
Definition: io_mgr.cpp:178
A PLUGIN derivation which could possibly be put into a DLL/DSO.
Definition: legacy_plugin.h:60
A PLUGIN derivation for saving and loading Pcbnew s-expression formatted files.
Definition: pcb_plugin.h:170
Releases a PLUGIN in the context of a potential thrown exception through its destructor.
Definition: io_mgr.h:564
A base class that BOARD loading and saving plugins should derive from.
Definition: io_mgr.h:270
virtual void Save(const wxString &aFileName, BOARD *aBoard, const STRING_UTF8_MAP *aProperties=nullptr)
Write aBoard to a storage file in a format that this PLUGIN implementation knows about or it can be u...
Definition: plugin.cpp:60
virtual BOARD * Load(const wxString &aFileName, BOARD *aAppendToMe, const STRING_UTF8_MAP *aProperties=nullptr, PROJECT *aProject=nullptr, PROGRESS_REPORTER *aProgressReporter=nullptr)
Load information from some input file format that this PLUGIN implementation knows about into either ...
Definition: plugin.cpp:46
virtual const wxString GetFileExtension() const =0
Returns the file extension for the PLUGIN.
A progress reporter interface for use in multi-threaded environments.
Container for project specific data.
Definition: project.h:63
A name/value tuple with unique names and optional values.
#define _(s)
Pcbnew PLUGIN for Fabmaster (Allegro) ASCII format.
const std::string KiCadFootprintLibPathExtension
const std::string EagleFootprintLibPathExtension
const std::string AltiumFootprintLibPathExtension
const std::string LegacyFootprintLibPathExtension
const std::string GedaPcbFootprintLibFileExtension
static IO_MGR::REGISTER_PLUGIN registerAltiumCircuitMakerPlugin(IO_MGR::ALTIUM_CIRCUIT_MAKER, wxT("Altium Circuit Maker"), []() -> PLUGIN *{ return new ALTIUM_CIRCUIT_MAKER_PLUGIN;})
static IO_MGR::REGISTER_PLUGIN registerCadstarArchivePlugin(IO_MGR::CADSTAR_PCB_ARCHIVE, wxT("CADSTAR PCB Archive"), []() -> PLUGIN *{ return new CADSTAR_PCB_ARCHIVE_PLUGIN;})
static IO_MGR::REGISTER_PLUGIN registerEaglePlugin(IO_MGR::EAGLE, wxT("Eagle"), []() -> PLUGIN *{ return new EAGLE_PLUGIN;})
static IO_MGR::REGISTER_PLUGIN registerAltiumDesignerPlugin(IO_MGR::ALTIUM_DESIGNER, wxT("Altium Designer"), []() -> PLUGIN *{ return new ALTIUM_DESIGNER_PLUGIN;})
static IO_MGR::REGISTER_PLUGIN registerFabmasterPlugin(IO_MGR::FABMASTER, wxT("Fabmaster"), []() -> PLUGIN *{ return new FABMASTER_PLUGIN;})
static IO_MGR::REGISTER_PLUGIN registerGPCBPlugin(IO_MGR::GEDA_PCB, wxT("GEDA/Pcb"), []() -> PLUGIN *{ return new GPCB_PLUGIN;})
#define FMT_NOTFOUND
Definition: io_mgr.cpp:43
static IO_MGR::REGISTER_PLUGIN registerPcadPlugin(IO_MGR::PCAD, wxT("P-Cad"), []() -> PLUGIN *{ return new PCAD_PLUGIN;})
static IO_MGR::REGISTER_PLUGIN registerKicadPlugin(IO_MGR::KICAD_SEXP, wxT("KiCad"), []() -> PLUGIN *{ return new PCB_PLUGIN;})
static IO_MGR::REGISTER_PLUGIN registerLegacyPlugin(IO_MGR::LEGACY, wxT("Legacy"), []() -> PLUGIN *{ return new LEGACY_PLUGIN;})
static IO_MGR::REGISTER_PLUGIN registerAltiumCircuitStudioPlugin(IO_MGR::ALTIUM_CIRCUIT_STUDIO, wxT("Altium Circuit Studio"), []() -> PLUGIN *{ return new ALTIUM_CIRCUIT_STUDIO_PLUGIN;})
#define THROW_IO_ERROR(msg)
Definition: ki_exception.h:38
Pcbnew PLUGIN for Altium *.PcbDoc format.
void Format(OUTPUTFORMATTER *out, int aNestLevel, int aCtl, const CPTREE &aTree)
Output a PTREE into s-expression format via an OUTPUTFORMATTER derivative.
Definition: ptree.cpp:200
Register a plugin.
Definition: io_mgr.h:139
Definition of file extensions used in Kicad.