##### Download

The `Xf_ThermSpinXferEvolve` OOMMF extension is a combination of the `Oxs_SpinXferEvolve` evolver that comes default with OOMMF, and the thermal fluctuation model that is in the `UHH_ThetaEvolve` evolver. The `Xf_ThermSpinXferEvolve` extension was created to allow the simultaneous simulation of spin-transfer torque and thermal fluctuation effects on a magnetic ensemble.

The spin torque equation derived by Sloczewski [1] and modified by Xiao [2] is written as (as implemented in OOMMF):

According to the OOMMF user guide:

has a default value of . In the definition of , is the reduced Planck’s constant, is the electronic charge in C, is the current density exerting spin-torque in , is the thickness of the free layer in meters in the direction which the current density is flowing, and is the saturation magnetization in . Note that may be rewritten as,

where is the current flowing homogeneously into the magnetic cell in A, and is the volume of the magnetic cell in .

and gives the in-plane and out-of-plane spin-torque terms, respectively. As implemented in OOMMF,

In the case where and , reduces to

The Specify block for the Xf_ThermSpinXferEvolve class has the form

Most of these options appear also in the `Oxs_EulerEvolve` class. The repeats have the same meaning as in that class, and the same default values except for `relative_step_error` and `error_rate`, which for `Xf_ThermSpinXferEvolve` have the default values of 0.01 and -1.0, respectively. Additionally, the ` alpha`,

`and`

**gamma_LL**`options may be initialized using scalar field objects, to allow these material parameters to vary spatially.`

**gamma_G**The default values for ** P** and

**are 0.4 and 2, respectively. If preferred, values for the fixed and free layers may be instead specified separately, through**

`Lambda`**,**

`P_fixed`**,**

`P_free`**, and**

`Lambda_fixed`**. Otherwise**

`Lambda_free``P_fixed`=

`P_free`=

`P`and

`Lambda_fixed`=

`Lambda_free`=

`Lambda`.

`Lambda`must be larger than or equal to 1; set

`Lambda`=1 to remove the dependence of on . If you want non-zero , it is set directly as

**.**

`eps_prime`Current density ** J** and unit polarization direction

**are required. The units on**

`mp`**are . Positive**

`J``J`produces torque that tends to align towards .

Simulation of domain-wall dynamics under current-induced spin-torque is enabled by setting ** propogate_mp** to 1. The setting

`propogate_mp`is 0 (disabled) by default. When

`propogate_mp`is enabled,

`mp`is actually , where is the flow direction and is the cell dimension in that direction. The flow direction may be set by setting

**as one of six options:**

`J_direction``-z`,

`+z`,

`-y`,

`+y`,

`-x`,

`+x`. The default is

`-z`. The direction changes the

`mp`used to calculate the spin torque at each cell site.

Parameters `J`, `mp`, `P`, `Lambda`, and `eps_prime` may all be varied pointwise (by specifying them as Oxs_ScalarField objects), but are fixed with respect to time. However, `J` can be multiplied by a time varying “profile,” to model current rise times, pulses, etc. Use the ** J_profile** and

**options to enable this feature. The**

`J_profile_args``Jprofile_script`should be a Tcl script that returns a single scalar.

`Jprofile_script_args`should be a subset of {stage stage_time total_time }, to specify arguments appended to

`Jprofile_script`on each time step. Default is the entire set, in the order as listed.

Simulations with thermal fluctuations are enabled using the parameters ** temperature** (in units of Kelvin). The parameter

`temperature`sets a constant temperature of thermal fluctuations. Heating effects may be simulated using the

`, which behaves similarly to`

**tempscript**`Jprofile`, to provide a time dependent scaling of

`temperature`. Only spatially uniform temperature is allowed in the simulation, and

`temperature`should be given as a scalar constant. The Tcl script given to

`tempscript`should also return a scalar. The arguments to

`tempscript`may be given as a list defined through

`tempscript_args`. The arguments in

`tempscript_args`should come from the following list: stage, stage_time, total_time.

The parameter ** uniform_seed** sets up the random number generator used to generate the thermal fluctuation field for thermal simulations. (Developmental note: thermal simulations seem to have random errors if this is not set during simulations with non-zero temperature.)

The ** allow_signed_gamma** parameter is for simulation testing purposes, and is intended for advanced use only. There is some lack of consistency in the literature with respect to the sign of . For this reason the Landau-Lifshitz-Gilbert equations are presented above using the absolute value of . This is the interpretation used if

**is 0 (the default). If instead**

`allow_signed_gamma`**is set to 1, then the Landau-Lifshitz-Gilbert equations are interpreted without the absolute values and with a sign change on the terms, i.e., the default value for in this case is (units are ). In this setting, if is set positive then the spins will precess backwards about the effective field, and the damping term will force the spins away from the effective field and increase the total energy. If you are experimenting with , you should either set to force spins back towards the effective field, or disable the energy precision control (discussed below).**

`allow_signed_gamma`The two controls ** min_step_headroom** (default value 0.33) and

**(default value 0.95) replace the single**

`max_step_headroom``step_headroom`option in

`Oxs_EulerEvolve`. The effective

`step_headroom`is automatically adjusted by the evolver between the

`min_headroom`and

`max_headroom`limits to make the observed reject proportion approach the

**(default value 0.05).**

`reject_goal`The ** method** entry selects a particular Runge-Kutta implementation. It should be set to one of

`rk2`,

`rk2heun`,

`rk4`,

`rkf54`,

`rkf54m`, or

`rkf54s`; the default value is

`rkf54`. The

`rk2`and

`rk4`methods implement canonical second and fourth global order Runge-Kutta methods [1], respectively. For

`rk2`, stepsize control is managed by comparing at the middle and final points of the interval, similar to what is done for stepsize control for the

`Oxs_EulerEvolve`class. One step of the

`rk2`method involves 2 evaluations of . The

`rk2heun`method implements Heun’s method and is essentially a modified version of the forward Euler method. Heun’s method calculates at the initial and the predict step, and uses the average of the two as the actual for calculating the next step.

In the `rk4` method, two successive steps are taken at half the nominal step size, and the difference between that end point and that obtained with one full size step are compared. The error is estimated at 1/15th the maximum difference between these two states. One step of the `rk4` method involves 11 evaluations of , but the end result is that of the 2 half-sized steps.

The remaining methods, `rkf54`, `rkf54m`, and `rkf54s`, are closely related Runge-Kutta-Fehlberg methods derived by Dormand and Prince [2, 3]. In the nomenclature of these papers, `rkf54` implements RK5(4)7FC, `rkf54m` implements RK5(4)7FM, and `rkf54s` implements RK5(4)7FS. All are 5th global order with an embedded 4th order method for stepsize control. Each step of these methods requires 6 evaluations of if the step is accepted, 7 if rejected. The difference between the methods involves tradeoffs between stability and error minimization. The RK5(4)7FS method has the best stability, RK5(4)7FM the smallest error, and RK5(4)7FC represents a compromise between the two. The default method used by `Oxs_RungeKuttaEvolve` is RK5(4)7FC.

The remaining undiscussed entry in the `Xf_ThermSpinXferEvolve` Specify block is ** energy_precision**. This should be set to an estimate of the expected relative accuracy of the energy calculation. After accounting for any change in the total energy arising from time-varying applied fields, the energy remainder should decrease from one step of the LLG ODE to the next.

`Xf_ThermSpinXferEvolve`will reject a step if the energy remainder is found to increase by more than that allowed by

`eprecision`. The default value for

`eprecision`is 1e-10. This control may be disabled by setting

`eprecision`to -1.

The `Xf_ThermSpinXferEvolve` module provides the same five scalar outputs and three vector outputs as `Oxs_RungeKuttaEvolve`, plus the scalar outputs “average J” and “Temperature,” and the vector field outputs “Spin torque” (which is ) and “J*mp.”

[1] J. Stoer and R. Bulirsch, Introduction to Numerical Analysis (Springer, New York, 1993), 2nd edn.

[2] J. R. Dormand and P. J. Prince, “A family of embedded Runge-Kutta formulae,” J. Comp. Appl. Math., **6**, 19-26 (1980)

[3] J. R. Dormand and P. J. Prince, “A reconsideration of some embedded Runge-Kutta formulae,” J. Comp. Appl. Math., **15**, 203-211 (1986).

Thank you very much for your sharing your source code. I’ve got one question about your code. And it lies in line 47 in xf_thermspinxferevolve_example1.mif. You set current_area as $width*$width. Why is it not $width*$lenth which means that the current is vertically injected, or $width*$thick which means that the current is injected in plane? I don’t quite understand the reason you set current_area as $width*$width.

Waiting for you reply.

Thank you again for your sharing your code.

Jinjun Ding

State Key Laboratory for Magnetism

Institute of Physics

Chinese Academy of Sciences

Beijing 100190, P.R. China

Phone: 0086-10-82648195

E-mail: jinjun.ding@gmail.com

LikeLike

Thanks for trying out the source code Jinjun. The examples simulate the injection of current vertically into only a portion of the magnet. In the examples, current is only injected into a cross-sectional area that is $width*$width.

Regards,

Xuanyao (Kelvin) Fong

LikeLike

Thank you very much for sharing this source code and I would like to follow up the question from Jinjun.

As you have said, $width*$width is used to inject a current only into that particular cross-sectional area. If I wish to change the direction of current from vertically into in-plane and so on, how would you go by doing that?

Thank you again for the code and Regards,

Patrick

LikeLike

Could you please tell me whether you have had so far any experience in using temperature scripts together with your source code in calculations involving temperature gradients?. If so, would you please share your experience in terms of how did you structure your temperature script and so on…

I look forward to hearing from you.

Brahim@MERL

Cambridge MA

LikeLike

Hi there,

How would you distinguish STT and SOT in this module?

Thanks.

LikeLike

STT and SOT are not distinguished in this module. All the Xf_STT allows you to do is to include different spin torques (either STT or SOT) into the simulation (for example by injecting current through both the heavy metal and the MTJ in an SOT MTJ structure).

This is achieved by mathematically rewriting expression of spin torque into a form that looks like a Zeeman field. Since Xf_STT is an energy class, it was written to not contribute to the energy of the system. OOMMF will include as many energy classes as declared and thus, the STT and SOT terms can be included as separate Xf_STT modules.

LikeLike

Hi Kevin,

Thank you very much for sharing this module, it has been very useful for me.

I have one question regarding the example:

proc dualPinnedLayers { xrel yrel zrel } {

if {$xrel 0.5, mp pointing up). Do you have any particular reason to set the mp has this spin polarization?

LikeLike

This example file is associated with the paper doi:10.1109/IMW.2013.6582105

LikeLike

Great thanks!

LikeLike

Good day dear Kevin.

Thank you very much for this module. Can I ask you a question regarding your examples?

I tested your examples, and I think your code seriously overestimates thermal fluctuations.

Even in the absence of external torque, it produces large deviations of the magnetization vector. I checked your source code, and it seems I know the problem.

In your code, you calculated the standard deviation of the distribution like sqrt((2*alpha*kb*T)/(mu0^2*gamma*Ms*V*dt)). In other words, it is proportional to 1/sqrt(dt). As far as I know, the conventional model of the Brownian motion (or Weiner process) tells that the standard deviation is proportional to sqrt(dt). Do you have any particular reason to add the dt into the denominator?

LikeLike

Hi Stanislav,

I think you might be confused between dm and dm/dt. The formulation says dm is proportional to sqrt(dt) and hence, dm/dt is proportional to 1/sqrt(dt). When the time integrator calculates m(t) from the initial value problem, it will multiply dm/dt with dt to solve for dm at every step, starting at m(t=0). The multiplication will result in dm being proportional to sqrt(dt) which is what you expect.

LikeLike

Thank you very much for your kind reply.

Excuse me, but I meant thermal field Hth, not dm/dt. As far as I know, the thermal fluctuations are represented by field Hth. And Hth should be proportional to sqrt(dt), but not dm/dt.The term sqrt((2*alpha*kb*T*dt)/(mu0^2*gamma*Ms*V))=dHth; therefore, Hth=dHth+Hth0. After calculations of all Fields, they will be integrated.

In the absence of the external torques, the magnetization vector will move towards the new random position of the Heff=Hanis+Hdemag+Hexch+Hth.

LikeLike

Hth cannot be proportional to sqrt(dt)

If it is, integrating over time will yield the “noise power” of Hth having a time dependence. This cannot be true. The only possibility is for Hth to have Hth to be proportional to 1/sqrt(dt)

LikeLike

Excuse me for my mistake.

dHth is proportional to sqrt(dt), not Hth. Hth modeled using the stochastic Wiener process. Such that dHth=Hth-Hth0=N(0,1)*(sigma^2). Where N(0,1) is a random number with a normal distribution. Sigma^2 is proportional to sqrt(dt). In the Wiener process, increments are independent of the previous values. However, the motion itself is continuous.

If you don’t mind, can we discuss it in more detail via e-mail?

Thank you very much.

LikeLike

Sure.

kelvin.xy.fong@nus.edu.sg

LikeLike

Hi Kevin,

I am trying to do SOT simulation using this module.But actually, I am suffering from an error which given as follows.

Error thrown from inside “Oxs_Director::GetAllScalarOutputs” — Error evaluating output “Max dm/dt” of object “Oxs_SpinXferEvolve:” — Oxs_Ext ERROR in object Oxs_SpinXferEvolve:: Oxs_SpinXferEvolve::UpdateDerivedOutputs: Can’t derive Delta E from single state.

(Oxs_Output)

————–

LikeLike

Hi Harikrishnan,

I recommend that you try using the 1.2a4 version of OOMMF with the module first. If the problems are still there, there is probably a compatibility issue with the module.

Best,

Kelvin FONG

LikeLike