From 57452b7f724ca60ff8fbd091c7c4f9eded92fc8b Mon Sep 17 00:00:00 2001 From: PhillipRambo <93056982+PhillipRambo@users.noreply.github.com> Date: Mon, 2 Dec 2024 13:12:12 +0100 Subject: [PATCH] Add files via upload --- .../part_1_OTA/scripting/OTA_low_gain.ipynb | 226 +++++++++--------- 1 file changed, 116 insertions(+), 110 deletions(-) diff --git a/modules/module_1_bandgap_reference/part_1_OTA/scripting/OTA_low_gain.ipynb b/modules/module_1_bandgap_reference/part_1_OTA/scripting/OTA_low_gain.ipynb index 399d5655..0a4caac0 100644 --- a/modules/module_1_bandgap_reference/part_1_OTA/scripting/OTA_low_gain.ipynb +++ b/modules/module_1_bandgap_reference/part_1_OTA/scripting/OTA_low_gain.ipynb @@ -2,14 +2,14 @@ "cells": [ { "cell_type": "code", - "execution_count": 1, + "execution_count": 122, "metadata": {}, "outputs": [], "source": [ "import numpy as np\n", "#for windows\n", - "#import sys\n", - "#sys.path.append(r'C:\\Users\\pedersen\\gmid') # path to gmid repository\n", + "import sys\n", + "sys.path.append(r'C:\\Users\\pedersen\\gmid') # path to gmid repository\n", "# ------\n", "import matplotlib.pyplot as plt\n", "from mosplot import load_lookup_table, LoadMosfet # make sure that mosplot can be found in the python path\n", @@ -21,12 +21,12 @@ }, { "cell_type": "code", - "execution_count": 2, + "execution_count": 123, "metadata": {}, "outputs": [], "source": [ - "pmos_lv_path = '/home/pedersen/chipdesign/cmos_analog/gmid_sweeps/pmos_lv_sweep.npy'\n", - "nmos_lv_path = '/home/pedersen/chipdesign/cmos_analog/gmid_sweeps/nmos_lv_sweep.npy'\n", + "pmos_lv_path = r'C:\\Users\\pedersen\\Desktop\\OpenDesingCourse/no_touch_files\\gmoveridpypmos_gmid_final.npy'\n", + "nmos_lv_path = r'C:\\Users\\pedersen\\Desktop\\OpenDesingCourse/no_touch_files\\gmoveridpynmos_final_gmid.npy'\n", "\n", "lookup_table_pmos = load_lookup_table(pmos_lv_path)\n", "lookup_table_nmos = load_lookup_table(nmos_lv_path)" @@ -34,7 +34,7 @@ }, { "cell_type": "code", - "execution_count": 3, + "execution_count": 124, "metadata": {}, "outputs": [], "source": [ @@ -44,7 +44,7 @@ }, { "cell_type": "code", - "execution_count": 4, + "execution_count": 125, "metadata": {}, "outputs": [], "source": [ @@ -237,35 +237,37 @@ }, { "cell_type": "code", - "execution_count": 5, + "execution_count": 126, "metadata": {}, "outputs": [], "source": [ "vdd = 1.2 # supply voltage\n", "Cl = 500e-15 # load capacitance\n", - "Av_wish = 80 # in db\n", - "phase_margin = 65 # At least :)\n", + "Av_wish = 75 # in db approximatly 70-75db\n", "fdominant = 1000 # dominant pole frequency\n", - "CC = 0.3*Cl \n", + "CC = Cl*1.5\n", "GBW = fdominant * dB_to_linear(Av_wish) # Gain Bandwidth Product" ] }, { - "cell_type": "markdown", + "cell_type": "code", + "execution_count": 127, "metadata": {}, + "outputs": [], "source": [ - "# First desigining the output stage looking at the output transistor" + "gm_M12 = GBW * CC * 2 * np.pi\n", + "gm_M6 = 15 * gm_M12" ] }, { "cell_type": "code", - "execution_count": 6, + "execution_count": 128, "metadata": {}, "outputs": [ { "data": { "application/vnd.jupyter.widget-view+json": { - "model_id": "32c41670fdbd48cd915f8cecbdd4fc9c", + "model_id": "7d85aaf18b7e4afb84f5464597cbeb06", "version_major": 2, "version_minor": 0 }, @@ -285,21 +287,21 @@ "gds_values_M6 = nmos_M6.extracted_table['gds']\n", "vgs_values_M6 = nmos_M6.extracted_table['vgs']\n", "\n", - "plot_data_vs_data(gm_values_M6/id_values_M6, gm_values_M6/gds_values_M6, vgs_values_M6, nmos_M6.extracted_table['lengths'], 'gm/id', 'gds')" + "plot_data_vs_data(gm_values_M6/id_values_M6, gm_values_M6/gds_values_M6, vgs_values_M6, nmos_M6.extracted_table['lengths'], 'gm/id', 'gm/gds')" ] }, { "cell_type": "code", - "execution_count": 26, + "execution_count": 129, "metadata": {}, "outputs": [ { "data": { "text/plain": [ - "6.283185307179587e-06" + "7.949913192125772e-05" ] }, - "execution_count": 26, + "execution_count": 129, "metadata": {}, "output_type": "execute_result" } @@ -308,7 +310,6 @@ "# For max gmro and vgs of 0.6V we have gmid of 5\n", "L_M6 = 9.75e-6\n", "gmid_M6 = 5 # strong inversion, i.e saturation\n", - "gm_M6 = 2*np.pi*GBW*Cl # we have se\n", "id_outputstage = gm_M6/gmid_M6\n", "gmro_M6 = 55.68\n", "ro_M6 = gmro_M6/gm_M6\n", @@ -317,21 +318,20 @@ }, { "cell_type": "code", - "execution_count": 27, + "execution_count": 130, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ - "gmro_M7 = 334.08\n" + "gmro_M7 = 222.72\n" ] } ], "source": [ "# Now for the pmos output transistor we must have 3 time the output impedance to insure max output gain\n", - "ro_M7 = 3*ro_M6\n", - "\n", + "ro_M7 = 2 * ro_M6\n", "# we want to place this transistor in moderate inversion\n", "gmid_M7 = 10\n", "gm_M7 = gmid_M7 * id_outputstage\n", @@ -341,13 +341,13 @@ }, { "cell_type": "code", - "execution_count": 28, + "execution_count": 131, "metadata": {}, "outputs": [ { "data": { "application/vnd.jupyter.widget-view+json": { - "model_id": "e631757f58a64118873cc3240a08af73", + "model_id": "833bb160c6a040f1aab4ff0562870238", "version_major": 2, "version_minor": 0 }, @@ -372,17 +372,18 @@ }, { "cell_type": "code", - "execution_count": 29, + "execution_count": 132, "metadata": {}, "outputs": [], "source": [ "# For the criteria to be met we must have \n", - "L_M7 = 3.38e-6" + "L_M7 = 2.08e-6\n", + "gmro_M7 = 390" ] }, { "cell_type": "code", - "execution_count": 30, + "execution_count": 133, "metadata": {}, "outputs": [ { @@ -391,7 +392,7 @@ "text": [ "L_M6 = 9.75e-06\n", "gmid_M6 = 5.00\n", - "L_M7 = 3.38e-06\n", + "L_M7 = 2.08e-06\n", "gmid_M7 = 10.00\n" ] } @@ -405,13 +406,13 @@ }, { "cell_type": "code", - "execution_count": 31, + "execution_count": 134, "metadata": {}, "outputs": [ { "data": { "application/vnd.jupyter.widget-view+json": { - "model_id": "f4c661be0d36403b8737fd91a618fdc7", + "model_id": "f844ac0b2e5c48ef9c44cf4f63247c08", "version_major": 2, "version_minor": 0 }, @@ -425,7 +426,7 @@ { "data": { "application/vnd.jupyter.widget-view+json": { - "model_id": "b2595dde5ebe43f3be4544582bafe044", + "model_id": "cf6424ea716549f4ad1dfc93487e5e34", "version_major": 2, "version_minor": 0 }, @@ -444,7 +445,7 @@ }, { "cell_type": "code", - "execution_count": 32, + "execution_count": 135, "metadata": {}, "outputs": [ { @@ -454,27 +455,27 @@ "\n", "Output Stage Amplification Summary\n", "Width and Lengths for M6\n", - " W = 2.28 um\n", + " W = 28.80 um\n", " L = 9.75 um\n", "Inversion Region for M6: Strong Inversion\n", "\n", "Width and Lengths for M7\n", - " W = 14.61 um\n", - " L = 3.38 um\n", + " W = 75.00 um\n", + " L = 2.08 um\n", "Inversion Region for M7: Strong Inversion\n", "\n", "Output Stage Bias:\n", - " Output Current : 6.28 μA\n", + " Output Current : 79.50 μA\n", "\n", "Output Stage Gain:\n", - " Av2 = 41.76 (32.42 dB)\n", + " Av2 = 37.12 (31.39 dB)\n", "\n" ] } ], "source": [ "id_over_W_M6 = 2.76\n", - "id_over_W_M7 = 0.43\n", + "id_over_W_M7 = 1.06\n", "\n", "display_outcurrent, unit_outcurrent = display_current(id_outputstage)\n", "Av2 = gm_M6 * (ro_M6 * ro_M7)/(ro_M6 + ro_M7)\n", @@ -514,25 +515,26 @@ }, { "cell_type": "code", - "execution_count": 33, + "execution_count": 136, "metadata": {}, "outputs": [ { "data": { "text/plain": [ - "1.392e-06" + "2.0004294796936965e-06" ] }, - "execution_count": 33, + "execution_count": 136, "metadata": {}, "output_type": "execute_result" } ], "source": [ "# Now we assume that the max gmro for our nmos in the input stage is 55.68\n", + "fp2 = gm_M6/(2*np.pi*Cl)\n", "gmro_M34_assumption = 55.68\n", "gmid_M34 = 5\n", - "Rout1 = 8e6\n", + "Rout1 = 1/(2*np.pi*fdominant* CC * (1 + Av2))\n", "gm_M34 = gmro_M34_assumption/Rout1\n", "id_branch = gm_M34/gmid_M34\n", "id_branch" @@ -540,21 +542,39 @@ }, { "cell_type": "code", - "execution_count": 34, + "execution_count": 137, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ - "gmro_M12 = 718.39\n", - "gmid_M12 = 21.50\n" + "mirror_pole_assumption = 20.95 MHz\n", + "fp2 = 126.52679816782855 MHz\n" + ] + } + ], + "source": [ + "mirror_pole_assumption = (gm_M34/( 4*np.pi*38e-15))*1e-6\n", + "print(f'mirror_pole_assumption = {mirror_pole_assumption:.2f} MHz')\n", + "print(f'fp2 = {fp2*1e-6:} MHz')" + ] + }, + { + "cell_type": "code", + "execution_count": 138, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "gmro_M12 = 442.56\n", + "gmid_M12 = 13.25\n" ] } ], "source": [ - "gm_M12 = dB_to_linear(float(Av_wish-Av2_db))/Rout1\n", - "CC = 1/(2*np.pi*fdominant* Rout1 * (1 + Av2))\n", "gmro_M12 = gm_M12 * Rout1*3\n", "gmid_M12 = gm_M12/id_branch\n", "print(f'gmro_M12 = {gmro_M12:.2f}')\n", @@ -570,13 +590,13 @@ }, { "cell_type": "code", - "execution_count": 35, + "execution_count": 139, "metadata": {}, "outputs": [ { "data": { "application/vnd.jupyter.widget-view+json": { - "model_id": "265f7ede0fd44c63a8c32143dc694ea6", + "model_id": "fa44bbefc0154f809fc62bb1f4a41d7e", "version_major": 2, "version_minor": 0 }, @@ -590,7 +610,7 @@ { "data": { "application/vnd.jupyter.widget-view+json": { - "model_id": "6b273b07c2044c82997f264b866c199d", + "model_id": "c792d4dd57d0406fa39ab7b9779bdb9c", "version_major": 2, "version_minor": 0 }, @@ -622,22 +642,22 @@ }, { "cell_type": "code", - "execution_count": 36, + "execution_count": 140, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ - "L_M12 = 3.25e-06\n", - "gmid_M12 = 21.50\n", + "L_M12 = 3.64e-06\n", + "gmid_M12 = 13.25\n", "L_M34 = 9.75e-06\n", "gmid_M34 = 5.00\n" ] } ], "source": [ - "L_M12 = 3.25e-6\n", + "L_M12 = 3.64e-6\n", "L_M34 = 9.75e-6\n", "\n", "print(f'L_M12 = {L_M12:.2e}')\n", @@ -649,13 +669,13 @@ }, { "cell_type": "code", - "execution_count": 37, + "execution_count": 141, "metadata": {}, "outputs": [ { "data": { "application/vnd.jupyter.widget-view+json": { - "model_id": "f996f78202ee479ba9ce8043d3049f46", + "model_id": "8cf6156d8983439b9e36b85a04dd0a8b", "version_major": 2, "version_minor": 0 }, @@ -669,7 +689,7 @@ { "data": { "application/vnd.jupyter.widget-view+json": { - "model_id": "18906fc315ab406b8bfd655e76f2e299", + "model_id": "a53493719c6f4501acf45f7f50192f97", "version_major": 2, "version_minor": 0 }, @@ -691,7 +711,7 @@ }, { "cell_type": "code", - "execution_count": 40, + "execution_count": 142, "metadata": {}, "outputs": [ { @@ -701,22 +721,22 @@ "\n", "Input Stage Amplification Summary\n", "Width and Lengths for M12\n", - " W = 27.84 um\n", - " L = 3.25 um\n", - "Inversion Region for M12: Weak Inversion\n", + " W = 7.41 um\n", + " L = 3.64 um\n", + "Inversion Region for M12: Moderate Inversion\n", "Width and Lengths for M34\n", - " W = 0.50 um\n", + " W = 0.72 um\n", " L = 9.75 um\n", "Inversion Region for M34: Strong Inversion\n", "Input Stage Bias:\n", - " Branch Current : 1.39 μA\n", - " input Tail current: 2.78 μA\n", + " Branch Current : 2.00 μA\n", + " input Tail current: 4.00 μA\n", "\n" ] } ], "source": [ - "id_over_W_M12 = 0.05\n", + "id_over_W_M12 = 0.27\n", "id_over_W_M34 = 2.76\n", "\n", "display_id_branch, unit_id_branch = display_current(id_branch)\n", @@ -724,8 +744,6 @@ "W_M12 = id_branch/id_over_W_M12\n", "W_M34 = id_branch/id_over_W_M34\n", "\n", - "Av1 = gm_M12*(ro_M12 * ro_M34/(ro_M12 + ro_M34))\n", - "\n", "\n", "input_stage_summary = f\"\"\"\n", "Input Stage Amplification Summary\n", @@ -746,7 +764,7 @@ }, { "cell_type": "code", - "execution_count": 44, + "execution_count": 143, "metadata": {}, "outputs": [ { @@ -760,44 +778,48 @@ " \n", "Output Stage Amplification Summary\n", "Width and Lengths for M6\n", - " W = 2.28 um\n", + " W = 28.80 um\n", " L = 9.75 um\n", "Inversion Region for M6: Strong Inversion\n", "\n", "Width and Lengths for M7\n", - " W = 14.61 um\n", - " L = 3.38 um\n", + " W = 75.00 um\n", + " L = 2.08 um\n", "Inversion Region for M7: Strong Inversion\n", "\n", "Output Stage Bias:\n", - " Output Current : 6.28 μA\n", + " Output Current : 79.50 μA\n", "\n", "Output Stage Gain:\n", - " Av2 = 41.76 (32.42 dB)\n", + " Av2 = 37.12 (31.39 dB)\n", "\n", "Input Stage:\n", " \n", "Input Stage Amplification Summary\n", "Width and Lengths for M12\n", - " W = 27.84 um\n", - " L = 3.25 um\n", - "Inversion Region for M12: Weak Inversion\n", + " W = 7.41 um\n", + " L = 3.64 um\n", + "Inversion Region for M12: Moderate Inversion\n", "Width and Lengths for M34\n", - " W = 0.50 um\n", + " W = 0.72 um\n", " L = 9.75 um\n", "Inversion Region for M34: Strong Inversion\n", "Input Stage Bias:\n", - " Branch Current : 1.39 μA\n", - " input Tail current: 2.78 μA\n", + " Branch Current : 2.00 μA\n", + " input Tail current: 4.00 μA\n", "\n", + " Input stage gain: 107.48 (40.63 dB)\n", "\n", "Gain and frequency response:\n", - " Gain Bandwidth Product: 10000000.0 Hz\n", + " Gain Bandwidth Product: 5623413.251903491 Hz\n", " Dominant Pole Frequency: 1000 Hz\n", - " Output Stage Compensation Capacitance: 4.652564987485247e-13 F\n", + " Output Stage Compensation Capacitance: 7.5e-13 F\n", " Load Capacitance: 5e-13 F\n", " dominant pole: 1000.0 Hz\n", - " non dominant pole: 10000000.000000002 Hz\n", + " non dominant pole: 126.52679816782855 MHz\n", + " mirror pole assumption: 20.945936842105265 MHz\n", + " Total gain: 3989.66 (72.02 dB)\n", + "\n", "\n", "\n" ] @@ -805,13 +827,14 @@ ], "source": [ "# summarizing everything\\\n", - "gmro_M12_actual = 800\n", + "gmro_M12_actual = 396\n", "ro_M12 = gmro_M12_actual/gm_M12\n", "ro_M34 = gmro_M34_assumption/gm_M34\n", "Av1 = gm_M12 * (ro_M12 * ro_M34)/(ro_M12 + ro_M34)\n", "f_pole_1 = 1/(2*np.pi * Rout1 * CC * (1 + Av2))\n", "f_pole_2 = gm_M6/(2*np.pi * Cl)\n", "\n", + "\n", "decades = (20*np.log10(Av1) + Av2_db) / 20\n", "\n", "if f_pole_1 * 10**decades < f_pole_2:\n", @@ -827,6 +850,7 @@ " {output_stage_summary}\n", "Input Stage:\n", " {input_stage_summary}\n", + " Input stage gain: {gm_M12 * (ro_M12 * ro_M34)/(ro_M12 + ro_M34):.2f} ({20*np.log10(gm_M12 * (ro_M12 * ro_M34)/(ro_M12 + ro_M34)):.2f} dB)\n", "\n", "Gain and frequency response:\n", " Gain Bandwidth Product: {GBW:} Hz\n", @@ -834,37 +858,19 @@ " Output Stage Compensation Capacitance: {CC:} F\n", " Load Capacitance: {Cl} F\n", " dominant pole: {f_pole_1} Hz\n", - " non dominant pole: {f_pole_2} Hz\n", + " non dominant pole: {f_pole_2*1e-6} MHz\n", + " mirror pole assumption: {mirror_pole_assumption} MHz\n", + " Total gain: {Av1*Av2:.2f} ({20*np.log10(Av1*Av2):.2f} dB)\n", + "\n", "\n", "\"\"\"\n", "print(summary)" ] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [] - }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [] } ], "metadata": { "kernelspec": { - "display_name": "Python 3 (ipykernel)", + "display_name": "Python 3", "language": "python", "name": "python3" }, @@ -878,7 +884,7 @@ "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", - "version": "3.10.12" + "version": "3.12.5" } }, "nbformat": 4,