Main Content

Field-Oriented Control of a Permanent Magnet Synchronous Machine

This example shows how to model a controller and implement it on a Xilinx® Zynq®-7000 All Programmable SoC target. This example uses a ZedBoard™ with an Analog Devices® motor control FMC board. If you do not have the required hardware, you can use this example to help you develop a controller for your own hardware configuration.


This example models a field-oriented controller (FOC) for a permanent magnet synchronous machine (PMSM), but you can apply the techniques shown in this example to develop most controller algorithms. This image shows the generalized workflow from model simulation to deployment of the controller algorithm onto an embedded hardware board.

Simulate a system test bench to gain insight into the behavior of the controller algorithm design. Then explore the design to see how the algorithm is partitioned. The high rate portion of the algorithm is partitioned into a model that is configured for HDL code generation. The low rate portion of the algorithm is partitioned into a model that is configured for C code generation. Generate C and HDL code from these models and learn how you can integrate this code into your design.

After exploring the algorithmic C and HDL code, automate deployment of the algorithmic code into reference frameworks for the processor and programmable logic. Then, execute a test on the deployed application, log the results, and compare them to the simulation results.

Because this example deploys a bitstream and ARM® executable to a Xilinx Zynq, you must set up the Xilinx Zynq hardware board prior to starting the example. To ensure the correct setup of your environment, complete the Getting Started with Targeting Xilinx Zynq Platform (HDL Coder) example with your hardware configuration prior to starting this example.


For more information about the hardware, see Zynq All Programmable SoC/Analog Devices Intelligent Drives Kit.

Simulate Algorithm Behavior

This section shows how to open the example project, inspect the controller models, and verify the controller behavior through simulation. This example is packaged as a project. For more information on Simulink® projects, see What Are Projects? (Simulink)

1. Run the zynqexPMSMFOCStart function to create and open a working copy of the project files for this example in a default MATLAB® projects folder. To choose a specific folder, use the absolute path of the folder as an input. The absolute path of the folder must be less than 80 characters.


2. Select Shortcut Management to view the shortcuts that this example uses.

3. Right-click the shortcut and identify the Open and Run Shortcut context menu items.

4. Run the task.t1_openSimulationTestBenchModel shortcut to open the focZynqTestBench model.


The Motor_And_Load subsystem consists of a mathematical model of a surface PMSM, motor load, encoder, and current sensor. The Controller_Algorithm subsystem includes an I/O engineering unit conversion, an electrical position calculation, a rotor velocity calculation, a mode scheduler, and four control modes (disabled, open loop velocity control, encoder calibration, and closed loop velocity control). The C/D and D/C subsystems convert the data from continuous-time, variable time step solver and floating-point data types, to discrete-time, fixed time step solver and fixed-point data types, simulation.

If you do not have Simscape Electrical™ installed, the Motor_And_Load subsystem contains a block that enables you to simulate the model with default motor and load parameters. In this case, you are not be able to explore or modify parameters.

5. On the Simulation tab of the Simulink Toolstrip, click Run to simulate the model.

6. When the model finishes running, open the Simulation Data Inspector. On the Simulation tab, click Data Inspector. For more information on the Simulation Data Inspector, see Simulation Data Inspector (Simulink).

7. In the Simulation Data Inspector, select the <commandType>, <velocityCommand>, <rotorVelocity>, and <controllerMode> signals.

For the first two seconds, the controller is commanded to calibrate the encoder position sensor. The encoder position sensor must be calibrated before the controller can achieve closed loop control. During the first portion of position calibration, the motor accelerates using open loop control in order to identify the index pulse of the encoder. Once the index is found, the controller commands and holds a zero position until the encoder offset is identified. During this period the velocity is zero. After two seconds, the controller changes into closed loop control and follows the commanded velocity profile. During closed loop velocity control, the FOC regulates phase current in the PMSM.

Partition Algorithm and Generate Code

This section shows you how the controller algorithm can be partitioned into complementary software and hardware implementations with generation of C and HDL code for the software and hardware implementations, respectively. Inspecting reports created during the code generation show how you can integrate this code into your own embedded design.

1. In the focZynqTestBench model, open the Controller_Algorithm subsystem. The controller algorithm contains the Algorithm_C and Algorithm_HDL blocks, which references the focZynqC and focZynqHDL models, respectively. The focZynqC model contains the portion of the algorithm to be implemented in software. Similarly, the focZynqHDL model contains the portion of the algorithm to be implemented on the hardware.

2. Run the task.t2_generateCCode function to open the focZynqC model, generate C code, and generate a report.


The focZynqC model contains the mode scheduler, velocity control loop, open-loop velocity controller, and routine to automatically calibrate the encoder offset.

3. The Code Generation Report shows how the generated code corresponds to the model. If you are new to the Code Generation report, you can start with the Code Interface Report to view the function interface of the code. The C code is portable and can be integrate with any floating-point embedded processor that uses ANSI-C compiler. For more information on the Code Generation Report, see Reports for Code Generation.

4. Run the task.t3_generateHdlCode function to open the focZynqHdl model, generate HDL code, and generate a report.


The focZynqHdl model contains the electrical position calculation, rotor velocity calculation, over-current checks, and the field-oriented controller.

5. The Code Generation Report shows how the HDL code corresponds to the model. If you are new to the Code Generation report, you can start by exploring the Generated Source Files pane of the report and selecting the focZynqHdl.vhd file that contains the entity specification. The HDL code for the algorithm is portable and can integrate with any FPGA that supports VHDL code.

Set Up Xilinx Zynq Platform and Motor Boards

This section shows you how to set up and connect the hardware boards listed in the Requirements section.

1. Run the Hardware Setup for the Xilinx Zynq platform. For information on the hardware setup, see Install Support for Xilinx Zynq Platform.

2. Connect the ZedBoard as shown.

3. Connect the AD-FMCMOTCON2-EBZ Controller board and ZedBoard as shown.

Deploy Bitstream to Programmable Logic

This section shows you how to use the HDL Workflow Advisor to generate HDL code for the algorithm, package HDL into an IP core, integrate the IP core into a Xilinx reference design, and create a bitstream.

1. Run the task.t4_openHdlWorkflowAdvisor function to open HDL Workflow Advisor.


2. On the HDL Workflow Advisor > 1. Set Target > 1.1 Set Target Device and Synthesis Tool group, the Target platform is set to ZedBoard and FMCMOTCON2. ZedBoard and FMCMOTCON2 is a Vivado® reference design containing the ADC, encoder, and PWM components. For information on how the creation of this reference design, see Define Custom Board and Reference Design for Zynq Workflow (HDL Coder).

3. Select 1.2. Set Target Interface to identify the ports. The Target Platform Interfaces with the prefix IP refer to connections that are registered with the ZedBoard motor control reference design.

4. Select 4.3 Build FPGA Bitstream > Run to Selected Task or run the task.t5_generateBitstreamAndInterfaceBlock function from the project to generate the HDL code for the algorithm and create the FPGA bitstream from the Xilinx reference design.


5. Follow the progress of bitstream generation on the new DOS Command Prompt that opens. In addition to generating a bitstream, additionally the customized target generates the focZynqHdlAxiInterfaceLib software interface library. The library contains an AXI_Interface block. The AXI_Interface block, which contains the AXI4-Lite interface components, provides connectivity from the model deployed on the ARM processor to the model deployed on the programmable logic.

6. Run task 4.4 Program Target Device or run the task.t6_downloadBitstream function from the project to program the FPGA.


Deploy Executable to ARM processor

This section shows how to generate C code for the controller and automate integrating this code with a Linux® reference framework to build, deploy, and run the model as an executable to the ARM processor. Data logged from the model running on the processor can then be compared the results of the simulation.

1. Run the task.t7_openZynqArmModel function to open the focZynqArmDeployment model.


The focZynqArmDeployment model can generate C code, automate integrating with a Linux ARM reference framework, and deploy the executable to the ARM processor on the Xilinx Zynq platform. The deployment model references the original controller model and contains test stimulus, scope, and AXI_Interface library block created in the Deploy Bitstream to Programmable Logic section.

2. On the Hardware tab, click Monitor & Tune to build, deploy, and run the model as an executable on the ARM processor. The generated code is compiled against the reference framework to create an executable. While executing, Simulink monitors the signals, showing them in the scope.

3. Open the Simulation Data Inspector to view the logged signals and compare them to the signals logged previously from focZynqTestBench model. On the Simulation tab, click Data Inspector.

4. In the Simulation Data Inspector, select the rotorVelocity signal. During the encoder calibration mode, the signals initially differ then agree since the simulated and real motors started with different rotor positions. In contrast, closed loop velocity control in simulation and hardware are very similar. Differences occur because the simulation model of the motor and sensors use data sheet values and do not explicitly account for the manufacturing tolerances of the physical motor.

Other Things to Try

  • Continue to explore the files in this example to gain more insight into how simulation, code generation, and automation deployment can help you develop a controller for your hardware.

  • HDL Coder™ supports floating-point single precision data types. Open a floating-point model of the example:

  • The floating-point model highlights the ability of HDL Coder to generate HDL code from a model containing a mix of fixed-point and floating-point data types. Follow the same tasks to implement the control algorithm with single-precision current control on a Xilinx Zynq SoC platform.