James M. Keller

274 papers A* 4A 1B 75C 7Journal 118Unranked 67
YearRankTypeTitle / Venue / Authors
2025 conf
FUZZ
Thomas A. Runkler, Wenlong Wu, James M. Keller
2025 J jnl
IEEE Access
Brendan J. Alvey, Brendan Young, James M. Keller
2025 J jnl
IEEE Trans. Emerg. Top. Comput. Intell.
Jeffrey J. Dale, James M. Keller, Aquila Galusha
2024 J jnl
IEEE Comput. Intell. Mag.
Míriam Mengíbar-Rodríguez, Jesús Chamorro-Martínez, James M. Keller
2024 B conf
IJCNN
Andrew R. Buck, Derek T. Anderson, James M. Keller, Cindy L. Bethel, Audrey L. Aldridge
2024 conf
FUZZ
Daphne Zou, Omar A. Ibrahim, James M. Keller
2024 conf
FUZZ
Brendan J. Alvey, Derek T. Anderson, James M. Keller
2024 conf
CAI
Timothy B. Gaines, Camden I. Boyle, James M. Keller, Matthew R. Maschmann, Stanton R. Price, Grant J. Scott
2024 conf
FUZZ
Brendan Young, Derek T. Anderson, James M. Keller, Fred Petry, Chris J. Michael
2023 conf
FUZZ
Andrew R. Buck, Derek T. Anderson, Raub Camaioni, Jack Akers, Robert H. Luke III, James M. Keller
2023 conf
FUZZ
Trevor M. Bajkowski, Noah Marchal, Jamal Saied-Walker, Pallavi Gupta, James M. Keller, Marjorie Skubic, Grant J. Scott
2023 conf
CAI
Brendan J. Alvey, Derek T. Anderson, James M. Keller
2023 conf
AIPR
Andrew R. Buck, Jack Akers, Derek T. Anderson, James M. Keller, Raub Camaioni, Matthew Deardorff, Robert H. Luke III
2023 conf
AIPR
Brendan Young, Derek T. Anderson, James M. Keller, Fred Petry, Chris J. Michael
2023 conf
FUZZ
Brendan Young, Derek T. Anderson, James M. Keller, Fred Petry, Chris J. Michael, Blake Ruprecht
2023 conf
FUZZ
Jeffrey Schulz, Derek T. Anderson, James M. Keller, Grant J. Scott, Robert H. Luke III
2023 conf
FUZZ
Wenlong Wu, James M. Keller, Marjorie Skubic, Mihail Popescu, Kari R. Lane, Marilyn Rantz
2023 conf
AIPR
Timothy B. Gaines, J. Alex Hurt, James M. Keller, Grant J. Scott, Camden I. Boyle, Matthew R. Maschmann, Stanton R. Price
2022 B conf
FUZZ-IEEE
Andrew R. Buck, Derek T. Anderson, James M. Keller, Robert H. Luke III, Grant J. Scott
2022 B conf
FUZZ-IEEE
Watchanan Chantapakul, James M. Keller, Sansanee Auephanwiriyakul
2022 B conf
FUZZ-IEEE
Wenlong Wu, James M. Keller, Marjorie Skubic, Mihail Popescu
2022 J jnl
IEEE Trans. Fuzzy Syst.
Carmen Martínez-Cruz, Antonio Jesús Rueda, Mihail Popescu, James M. Keller
2022 J jnl
IEEE Trans. Emerg. Top. Comput. Intell.
Wenlong Wu, James M. Keller, Jeffrey Dale, James C. Bezdek
2021 B conf
FUZZ-IEEE
Andrew R. Buck, Derek T. Anderson, James M. Keller, Robert H. Luke III, Grant J. Scott
2021 conf
SSCI
Brendan Alvey, Derek T. Anderson, Clare Yang, Andrew R. Buck, James M. Keller, Ken E. Yasuda, Hollie A. Ryan
2021 J jnl
IEEE Trans. Fuzzy Syst.
Rayan Gargees, James M. Keller, Mihail Popescu
2021 J jnl
ACM Trans. Comput. Heal.
Wenlong Wu, James M. Keller, Marjorie Skubic, Mihail Popescu, Kari R. Lane
2021 J jnl
IEEE Trans. Emerg. Top. Comput. Intell.
Omar A. Ibrahim, James M. Keller, James C. Bezdek
2021 conf
AIPR
Trevor M. Bajkowski, J. Alex Hurt, Jeffrey Dale, David Huangal, James M. Keller, Grant J. Scott, Stanton R. Price
2021 J jnl
IEEE Trans. Emerg. Top. Comput. Intell.
Bryce J. Murray, Muhammad Aminul Islam, Anthony J. Pinar, Derek T. Anderson, Grant J. Scott, Timothy C. Havens, James M. Keller
2021 conf
ICCVW
Brendan Alvey, Derek T. Anderson, Andrew R. Buck, Matthew Deardorff, Grant J. Scott, James M. Keller
2021 J jnl
IEEE Trans. Syst. Man Cybern. Syst.
James C. Bezdek, James M. Keller
2021 J jnl
IEEE Trans. Fuzzy Syst.
Rayan Gargees, James M. Keller, Mihail Popescu
2020 B conf
FUZZ-IEEE
Andrew R. Buck, Derek T. Anderson, James M. Keller, Timothy Wilkin, Muhammad Aminul Islam
2020 J jnl
IEEE Comput. Intell. Mag.
Timothy C. Havens, James M. Keller
2020 J jnl
IEEE Trans. Biomed. Eng.
Giovanna Guidoboni, Lorenzo Sala, Moein Enayati, Riccardo Sacco, Marcela Szopos, James M. Keller, Mihail Popescu, Laurel Despins, Virginia H. Huxley, Marjorie Skubic
2020 conf
AIPR
Jeffrey J. Dale, David Huangal, J. Alex Hurt, Trevor M. Bajkowski, James M. Keller, Grant J. Scott, Stanton R. Price
2020 J jnl
IEEE Trans. Fuzzy Syst.
Muhammad Aminul Islam, Derek T. Anderson, Anthony J. Pinar, Timothy C. Havens, Grant J. Scott, James M. Keller
2020 J jnl
IEEE Trans. Fuzzy Syst.
Jesús Chamorro-Martínez, James M. Keller
2020 B conf
FUZZ-IEEE
Jesús Chamorro-Martínez, Míriam Mengíbar-Rodríguez, James M. Keller
2020 B conf
FUZZ-IEEE
Wenlong Wu, James M. Keller
2020 conf
AIPR
Trevor M. Bajkowski, David Huangal, J. Alex Hurt, Jeffrey Dale, James M. Keller, Grant J. Scott, Stanton R. Price
2020 J jnl
CoRR
Wenlong Wu, James M. Keller, Jeffrey Dale, James C. Bezdek
2019 B conf
FUZZ-IEEE
Omar A. Ibrahim, James M. Keller, Mihail Popescu
2019 J jnl
IEEE Trans. Biomed. Eng.
Giovanna Guidoboni, Lorenzo Sala, Moein Enayati, Riccardo Sacco, Marcela Szopos, James M. Keller, Mihail Popescu, Laurel Despins, Virginia H. Huxley, Marjorie Skubic
2019 B conf
FUZZ-IEEE
Wenlong Wu, James M. Keller, Marjorie Skubic, Mihail Popescu
2019 J jnl
Int. J. Data Min. Bioinform.
Hasanain Al-Sadr, Mihail Popescu, James M. Keller
2019 J jnl
CoRR
Muhammad Aminul Islam, Derek T. Anderson, Anthony J. Pinar, Timothy C. Havens, Grant J. Scott, James M. Keller
2019 B conf
FUZZ-IEEE
Andrew R. Buck, James M. Keller
2019 J jnl
IEEE Comput. Intell. Mag.
Enrique H. Ruspini, James C. Bezdek, James M. Keller
2019 B conf
FUZZ-IEEE
Charlie T. Veal, Alex Yang, J. Alex Hurt, Muhammad Aminul Islam, Derek T. Anderson, Grant J. Scott, James M. Keller, Timothy C. Havens, Bo Tang
2019 J jnl
J. Biomed. Informatics
Akshay Jain, Mihail Popescu, James M. Keller, Marilyn Rantz, Brianna Markway
2019 conf
BHI
Ruhan Yi, Moein Enayati, James M. Keller, Mihail Popescu, Marjorie Skubic
2019 C conf
ICOST
Rayan Gargees, James M. Keller, Mihail Popescu, Marjorie Skubic
2018 J jnl
Int. J. Approx. Reason.
Pedro Manuel Martínez-Jiménez, Jesús Chamorro-Martínez, James M. Keller
2018 J jnl
Int. J. Uncertain. Fuzziness Knowl. Based Syst.
Omar A. Ibrahim, Yiqing Wang, James M. Keller
2018 B conf
FUZZ-IEEE
Omar A. Ibrahim, James M. Keller, James C. Bezdek
2018 conf
BIBM
Hasanain Al-Sadr, Mihail Popescu, James M. Keller
2018 J jnl
IEEE Trans. Fuzzy Syst.
James C. Bezdek, James M. Keller, Nikhil R. Pal, Chin-Teng Lin, Jonathan M. Garibaldi
2018 B conf
FUZZ-IEEE
Wenlong Wu, James M. Keller, Thomas A. Runkler
2018 conf
EMBC
Moein Enayati, Marjorie Skubic, James M. Keller, Mihail Popescu, Nasibeh Zanjirani Farahani
2017 J jnl
J. Ambient Intell. Smart Environ.
Tanvi Banerjee, Maria Yefimova, James M. Keller, Marjorie Skubic, Diana Lynn Woods, Marilyn Rantz
2017 B conf
FUZZ-IEEE
Thomas A. Runkler, James M. Keller
2016 B conf
CEC
Andrew R. Buck, James M. Keller
2016 B conf
FUZZ-IEEE
Omar A. Ibrahim, Jingyi Shao, James M. Keller, Mihail Popescu
2016 conf
IPMU (1)
Leary Tomlin, Derek T. Anderson, Christian Wagner, Timothy C. Havens, James M. Keller
2016 conf
IPMU (1)
Akshay Jain, Tianqi Jiang, James M. Keller
2016 B conf
CEC
Xiaoxiao Du, Alina Zare, James M. Keller, Derek T. Anderson
2016 conf
BHI
Akshay Jain, James M. Keller, James C. Bezdek
2016 B conf
FUZZ-IEEE
Mihail Popescu, James M. Keller
2016 conf
EMBC
Jialei Yang, James M. Keller, Mihail Popescu, Marjorie Skubic
2015 B conf
FUZZ-IEEE
Akshay Jain, James M. Keller
2015 J jnl
Comput. Vis. Image Underst.
Tanvi Banerjee, James M. Keller, Mihail Popescu, Marjorie Skubic
2015 conf
EMBC
Akshay Jain, James M. Keller
2014 conf
CIBD
James M. Keller, Andrew R. Buck, Alina Zare, Mihail Popescu
2014 B conf
FUZZ-IEEE
Tanvi Banerjee, James M. Keller, Marjorie Skubic
2014 J jnl
IEEE Trans. Fuzzy Syst.
Tanvi Banerjee, James M. Keller, Marjorie Skubic, Erik E. Stone
2014 conf
IPMU (1)
Lequn Hu, Derek T. Anderson, Timothy C. Havens, James M. Keller
2014 conf
CIBD
Andrew R. Buck, Alina Zare, James M. Keller, Mihail Popescu
2014 conf
IEEE Conf. on Intelligent Systems (1)
Anna Wilbik, Uzay Kaymak, James M. Keller, Mihail Popescu
2014 B conf
IEEE Congress on Evolutionary Computation
Andrew R. Buck, Tanvi Banerjee, James M. Keller
2014 J jnl
IEEE Trans. Fuzzy Syst.
Derek T. Anderson, Timothy C. Havens, Christian Wagner, James M. Keller, Melissa F. Anderson, Daniel J. Wescott
2014 J jnl
Pattern Recognit.
Mohammed Khalilia, James C. Bezdek, Mihail Popescu, James M. Keller
2014 J jnl
IEEE Trans. Fuzzy Syst.
Anna Wilbik, James M. Keller, James C. Bezdek
2014 conf
EMBC
Tanvi Banerjee, Moein Enayati, James M. Keller, Marjorie Skubic, Mihail Popescu, Marilyn Rantz
2014 J jnl
IEEE J. Biomed. Health Informatics
Tanvi Banerjee, Marjorie Skubic, James M. Keller, Carmen Abbott
2014 conf
CIES
Andrew R. Buck, James M. Keller
2013 J jnl
IEEE Trans. Cybern.
Mihail Popescu, James C. Bezdek, Timothy C. Havens, James M. Keller
2013 J jnl
IEEE Trans. Fuzzy Syst.
Anna Wilbik, James M. Keller
2013 J jnl
IEEE Trans. Evol. Comput.
Andrew R. Buck, James M. Keller, Marjorie Skubic
2013 conf
CICAC
Mihail Popescu, James M. Keller, Alina Zare
2013 conf
Memetic Computing
Andrew R. Buck, James M. Keller
2013 conf
WCSC
Andrew R. Buck, James M. Keller, Mihail Popescu
2013 B conf
FUZZ-IEEE
Anna Wilbik, James M. Keller
2013 B conf
FUZZ-IEEE
Tanvi Banerjee, James M. Keller, Marjorie Skubic
2013 J jnl
IEEE Trans. Geosci. Remote. Sens.
Matthew N. Klaric, Brian C. Claywell, Grant J. Scott, Nicholas J. Hudson, Ozy Sjahputera, Yonghong Li, Seth T. Barratt, James M. Keller, Curt H. Davis
2013 conf
WCSC
Stanton R. Price, Derek T. Anderson, Christian Wagner, Timothy C. Havens, James M. Keller
2013 J jnl
IEEE J. Biomed. Health Informatics
Fang Wang, Erik E. Stone, Marjorie Skubic, James M. Keller, Carmen Abbott, Marilyn Rantz
2012 J jnl
Fuzzy Sets Syst.
Anna Wilbik, James M. Keller
2012 C conf
IGARSS
Alina Zare, Zachary Fields, James M. Keller, Joshua Horton
2012 C conf
IGARSS
James M. Keller, Mihail Popescu, Dustin Gibeson
2012 conf
CISDA
Derek T. Anderson, Ozy Sjahputera, Kevin E. Stone, James M. Keller
2012 J jnl
IEEE J. Sel. Top. Appl. Earth Obs. Remote. Sens.
Derek T. Anderson, Kevin E. Stone, James M. Keller, Christopher J. Spain
2012 conf
CISDA
Mihail Popescu, Alex Paino, Kevin E. Stone, James M. Keller
2012 conf
CISDA
David B. Lewis, James M. Keller, Mihail Popescu, Kevin E. Stone
2012 B conf
FUZZ-IEEE
Thomas A. Runkler, James M. Keller
2012 B conf
FUZZ-IEEE
Anna Wilbik, James M. Keller, James C. Bezdek
2012 C conf
IGARSS
Mihail Popescu, James M. Keller
2012 conf
EMBC
Tanvi Banerjee, James M. Keller, Marjorie Skubic
2012 J jnl
Int. J. Intell. Syst.
Anna Wilbik, James M. Keller, Gregory L. Alexander
2012 J jnl
Int. J. Intell. Syst.
Derek T. Anderson, María Ros, James M. Keller, Manuel P. Cuéllar, Mihail Popescu, Miguel Delgado, Maria-Amparo Vila
2012 B conf
FUZZ-IEEE
Derek T. Anderson, Timothy C. Havens, Christian Wagner, James M. Keller, Melissa F. Anderson, Daniel J. Wescott
2011 J jnl
IEEE Comput. Intell. Mag.
James M. Keller
2011 conf
AIPR
Tyler Gill, James M. Keller, Derek T. Anderson, Robert H. Luke III
2011 J jnl
Pattern Recognit.
Masud Moshtaghi, Timothy C. Havens, James C. Bezdek, Laurence Anthony F. Park, Christopher Leckie, Sutharshan Rajasegarar, James M. Keller, Marimuthu Palaniswami
2011 J jnl
IEEE Trans. Geosci. Remote. Sens.
Ozy Sjahputera, Grant J. Scott, Brian C. Claywell, Matthew N. Klaric, Nicholas J. Hudson, James M. Keller, Curt H. Davis
2011 B conf
FUZZ-IEEE
Derek T. Anderson, James M. Keller, Ozy Sjahputera, James C. Bezdek, Mihail Popescu
2011 J jnl
IEEE Geosci. Remote. Sens. Lett.
Isaac J. Sledge, James M. Keller, Wenbo Song, Curt H. Davis
2011 B conf
SMC
Mihail Popescu, James M. Keller, James C. Bezdek, Timothy C. Havens
2011 conf
AIPR
Derek T. Anderson, Justin Farrell, Kevin E. Stone, James M. Keller, Christopher J. Spain
2011 B conf
CogSci
Marjorie Skubic, Samuel N. Blisard, Robert H. Luke III, Erik E. Stone, Derek T. Anderson, James M. Keller
2011 B conf
FUZZ-IEEE
Derek T. Anderson, James M. Keller, Melissa F. Anderson, Daniel J. Wescott
2011 B conf
FUZZ-IEEE
María Ros, Manuel Pegalajar Cuéllar, Miguel Delgado, Maria-Amparo Vila, Derek T. Anderson, James M. Keller, Mihail Popescu
2011 B conf
SMC
Anna Wilbik, James M. Keller, Gregory L. Alexander
2011 conf
EMBC
Zhongna Zhou, Erik Edward Stone, Marjorie Skubic, James M. Keller, Zhihai He
2011 conf
CISDA
Andrew R. Buck, James M. Keller, Marjorie Skubic, Marcin Detyniecki, Thomas Bärecke
2011 conf
EMBC
Fang Wang, Marjorie Skubic, Carmen Abbott, James M. Keller
2011 J jnl
Trans. GIS
Wenbo Song, James M. Keller, Timothy L. Haithcoat, Curt H. Davis
2010 conf
IPMU (1)
Derek T. Anderson, James C. Bezdek, James M. Keller, Mihail Popescu
2010 conf
ICAISC (1)
Timothy C. Havens, James C. Bezdek, James M. Keller
2010 B conf
FUZZ-IEEE
Timothy C. Havens, Derek T. Anderson, James M. Keller
2010 B conf
IEEE Congress on Evolutionary Computation
Andrew R. Buck, James M. Keller, Marjorie Skubic
2010 B conf
FUZZ-IEEE
Isaac J. Sledge, James C. Bezdek, Timothy C. Havens, James M. Keller
2010 B conf
FUZZ-IEEE
James C. Bezdek, Timothy C. Havens, James M. Keller, Christopher Leckie, Laurence Anthony F. Park
2010 C conf
IGARSS
Ozy Sjahputera, Grant J. Scott, Matthew N. Klaric, Brian C. Claywell, Nicholas J. Hudson, James M. Keller, Curt H. Davis
2010 J jnl
IEEE Trans. Fuzzy Syst.
Derek T. Anderson, James C. Bezdek, Mihail Popescu, James M. Keller
2010 J jnl
IEEE Trans. Fuzzy Syst.
Timothy C. Havens, James M. Keller, Mihail Popescu
2010 C conf
IPMU
Derek T. Anderson, James M. Keller, Timothy C. Havens
2010 J jnl
IEEE Trans. Fuzzy Syst.
Isaac J. Sledge, Timothy C. Havens, James C. Bezdek, James M. Keller
2010 J jnl
IEEE Trans. Fuzzy Syst.
Isaac J. Sledge, James C. Bezdek, Timothy C. Havens, James M. Keller
2010 B conf
FUZZ-IEEE
Derek T. Anderson, Robert H. Luke III, James M. Keller
2010 B conf
FUZZ-IEEE
Tanvi Banerjee, James M. Keller, Marjorie Skubic, Carmen Abbott
2009 J jnl
IEEE Trans. Image Process.
Wenbo Song, James M. Keller, Timothy L. Haithcoat, Curt H. Davis
2009 J jnl
Int. J. Intell. Syst.
Timothy C. Havens, James C. Bezdek, James M. Keller, Mihail Popescu
2009 conf
CIVI
Timothy C. Havens, Gregory L. Alexander, Carmen Abbott, James M. Keller, Marjorie Skubic, Marilyn Rantz
2009 J jnl
Soft Comput.
Isaac J. Sledge, Timothy C. Havens, Jacalyn M. Huband, James C. Bezdek, James M. Keller
2009 conf
IFSA/EUSFLAT Conf.
Robert H. Luke III, Derek Anderson, James M. Keller, Simon Coupland
2009 conf
IFSA/EUSFLAT Conf.
Derek Anderson, Robert H. Luke III, Erik E. Stone, James M. Keller
2009 B conf
FUZZ-IEEE
Timothy C. Havens, Gregory L. Alexander, James M. Keller, Marjorie Skubic, Marilyn Rantz
2009 J jnl
Ann. Math. Artif. Intell.
Timothy C. Havens, James C. Bezdek, James M. Keller, Mihail Popescu, Jacalyn M. Huband
2009 J jnl
Comput. Vis. Image Underst.
Derek Anderson, Robert H. Luke III, James M. Keller, Marjorie Skubic, Marilyn Rantz, Myra Aud
2009 B conf
FUZZ-IEEE
Isaac J. Sledge, James M. Keller
2009 J jnl
IEEE Trans. Fuzzy Syst.
Derek Anderson, Robert H. Luke III, James M. Keller, Marjorie Skubic, Marilyn Rantz, Myra Aud
2009 C conf
ISCAS
Zhongna Zhou, Xi Chen, Yu-Chia Chung, Zhihai He, Tony X. Han, James M. Keller
2009 B conf
FUZZ-IEEE
Mihail Popescu, James C. Bezdek, James M. Keller
2008 B conf
FUZZ-IEEE
Mihail Popescu, James C. Bezdek, James M. Keller, Timothy C. Havens, Jacalyn M. Huband
2008 J jnl
IEEE Trans. Circuits Syst. Video Technol.
Zhongna Zhou, Xi Chen, Yu-Chia Chung, Zhihai He, Tony X. Han, James M. Keller
2008 book
Dong Xu, James M. Keller, Mihail Popescu, Rajkumar Bondugula
2008 B conf
ICPR
Timothy C. Havens, James C. Bezdek, James M. Keller, Mihail Popescu
2008 B conf
FUZZ-IEEE
Derek Anderson, Robert H. Luke III, James M. Keller, Marjorie Skubic
2008 conf
IGARSS (5)
Ozy Sjahputera, Curt H. Davis, Brian C. Claywell, Nicholas J. Hudson, James M. Keller, Michael G. Vincent, Yonghong Li, Matthew N. Klaric, Chi-Ren Shyu
2008 B conf
ICPR
Isaac J. Sledge, James M. Keller
2008 J jnl
IEEE Trans. Fuzzy Syst.
Andres Mendez-Vazquez, Paul D. Gader, James M. Keller, Kenneth Chamberlin
2008 B conf
FUZZ-IEEE
Timothy C. Havens, James M. Keller, Mihail Popescu, James C. Bezdek
2008 conf
SIS
Timothy C. Havens, Christopher J. Spain, Nathan G. Salmon, James M. Keller
2008 J jnl
IEEE Trans. Fuzzy Syst.
Derek T. Anderson, Robert H. Luke III, James M. Keller
2008 B conf
IEEE Congress on Evolutionary Computation
Nicholas Harvey, Robert H. Luke III, James M. Keller, Derek Anderson
2008 conf
AAAI Fall Symposium: AI in Eldercare: New Solutions to Old Problems
Isaac J. Sledge, James M. Keller, Timothy C. Havens, Gregory L. Alexander, Marge Skubic
2008 conf
AAAI Fall Symposium: AI in Eldercare: New Solutions to Old Problems
Marilyn Rantz, Myra Aud, Gregory L. Alexander, Debra Parker Oliver, De Minner, Marge Skubic, James M. Keller, Zhihai He, Mihail Popescu, George Demiris, Steven J. Miller
2007 A* conf
ICRA
Mark A. Busch, Marjorie Skubic, James M. Keller, Kevin E. Stone
2007 J jnl
IEEE Trans. Geosci. Remote. Sens.
Tsaipei Wang, James M. Keller, Paul D. Gader, Ozy Sjahputera
2007 ch.
Analysis and Design of Intelligent Systems using Soft Computing Techniques
Derek Anderson, Robert H. Luke III, James M. Keller
2007 conf
FOCI
Gaurav Parekh, James M. Keller
2007 J jnl
IEEE ACM Trans. Comput. Biol. Bioinform.
Ozy Sjahputera, James M. Keller, J. Wade Davis, Kristen H. Taylor, Farahnaz Rahmatpanah, Huidong Shi, Derek Anderson, Samuel Blisard, Robert H. Luke III, Mihail Popescu, Gerald C. Arthur, Charles William Caldwell
2007 A* conf
ICRA
Gaurav Parekh, Marjorie Skubic, Ozy Sjahputera, James M. Keller
2007 J jnl
Fuzzy Sets Syst.
Ozy Sjahputera, James M. Keller
2006 A* conf
HRI
Samuel Blisard, Marjorie Skubic, Robert H. Luke III, James M. Keller
2006 B conf
FUZZ-IEEE
Xi Chen, Zhihai He, James M. Keller, Derek Anderson, Marjorie Skubic
2006 B conf
ICIP
Xi Chen, Zhihai He, Derek Anderson, James M. Keller, Marjorie Skubic
2006 B conf
FUZZ-IEEE
Shuang Wang, James M. Keller, Kathryn Burks, Marjorie Skubic, Harry W. Tyrer
2006 B conf
FUZZ-IEEE
Dong Xu, Rajkumar Bondugula, Mihail Popescu, James M. Keller
2006 J jnl
IEEE ACM Trans. Comput. Biol. Bioinform.
Mihail Popescu, James M. Keller, Joyce A. Mitchell
2006 J jnl
IEEE Trans. Fuzzy Syst.
Mihail Popescu, Paul D. Gader, James M. Keller
2006 J jnl
Int. J. Uncertain. Fuzziness Knowl. Based Syst.
James M. Keller, James C. Bezdek, Mihail Popescu, Nikhil R. Pal, Joyce A. Mitchell, Jacalyn M. Huband
2006 B conf
SMC
Tsaipei Wang, James M. Keller
2006 conf
EMBC
Derek Anderson, James M. Keller, Marjorie Skubic, Xi Chen, Zhihai He
2006 B conf
FUZZ-IEEE
Mihail Popescu, James M. Keller
2006 conf
EMBC
Harry W. Tyrer, Majd Alwan, George Demiris, Zhihai He, James M. Keller, Marjorie Skubic, Marilyn Rantz
2005 J jnl
IEEE Trans. Fuzzy Syst.
Nikhil R. Pal, Kuhu Pal, James M. Keller, James C. Bezdek
2005 A conf
IROS
Robert H. Luke III, James M. Keller, Marjorie Skubic, Steven Senger
2005 B conf
FUZZ-IEEE
Mihail Popescu, James M. Keller, Joyce A. Mitchell
2005 J jnl
Neural Parallel Sci. Comput.
Nikhil R. Pal, James M. Keller, Mihail Popescu, James C. Bezdek, Joyce A. Mitchell, Jacalyn M. Huband
2005 B conf
RO-MAN
Robert H. Luke III, Blisard N., James M. Keller, Marjorie Skubic
2005 conf
SIS
Ozy Sjahputera, James M. Keller
2005 conf
EUSFLAT Conf.
Ozy Sjahputera, James M. Keller
2005 J jnl
Int. J. Intell. Syst.
Kuhu Pal, Nikhil R. Pal, James M. Keller, James C. Bezdek
2005 conf
EUSFLAT Conf.
James M. Keller
2005 B conf
FUZZ-IEEE
James M. Keller, Mihail Popescu
2004 conf
AAAI Technical Report (5)
Marjorie Skubic, David C. Noelle, D. Mitch Wilkes, Kazuhiko Kawamura, James M. Keller
2004 B conf
FUZZ-IEEE
Nikhil R. Pal, Kuhu Pal, James M. Keller, James C. Bezdek
2004 J jnl
IEEE Trans. Fuzzy Syst.
James M. Keller, Nikhil R. Pal
2004 conf
Neural Networks and Computational Intelligence
Rajkumar Bondugula, Pascal Matsakis, James M. Keller
2004 B conf
FUZZ-IEEE
James M. Keller, Mihail Popescu, Joyce A. Mitchell
2004 J jnl
IEEE Trans. Pattern Anal. Mach. Intell.
Pascal Matsakis, James M. Keller, Ozy Sjahputera, Jonathon Marjamaa
2003 B conf
FUZZ-IEEE
Tsaipei Wang, James M. Keller, Gerhard W. Cibis
2003 B conf
FUZZ-IEEE
Hyo-Jin Suh, James M. Keller, C. Andrew Carson
2003 B conf
FUZZ-IEEE
Grant J. Scott, James M. Keller, Marjorie Skubic, Robert H. Luke III
2003 J jnl
Auton. Robots
Marjorie Skubic, Pascal Matsakis, George Chronis, James M. Keller
2003 B conf
FUZZ-IEEE
Mihail Popescu, James M. Keller, Paul D. Gader
2003 B conf
FUZZ-IEEE
Anupam Joshi, James M. Keller, Olfa Nasraoui
2003 B conf
FUZZ-IEEE
Ozy Sjahputera, James M. Keller, Pascal Matsakis, Rajkumar Bondugula
2002 J jnl
IEEE Trans. Fuzzy Syst.
Sansanee Auephanwiriyakul, James M. Keller
2002 J jnl
Inf. Fusion
Sansanee Auephanwiriyakul, James M. Keller, Paul D. Gader
2002 B conf
FUZZ-IEEE
Sansanee Auephanwiriyakul, Allyson D. Adrian, James M. Keller
2001 B conf
FUZZ-IEEE
Sansanee Auephanwiriyakul, James M. Keller
2001 J jnl
J. Intell. Fuzzy Syst.
David DeKruger, Jesse Hodge, James C. Bezdek, James M. Keller, Paul D. Gader
2001 J jnl
IEEE Trans. Syst. Man Cybern. Part B
Zhi-Qiang Liu, Leonard T. Bruton, James C. Bezdek, James M. Keller, Sandy Dance, N. R. Bartley, Cishen Zhang
2001 B conf
FUZZ-IEEE
Pascal Matsakis, Jonathon Marjamaa, Ozy Sjahputera, James M. Keller
2001 A* conf
ICRA
Marjorie Skubic, George Chronis, Pascal Matsakis, James M. Keller
2001 J jnl
IEEE Trans. Syst. Man Cybern. Part B
Pascal Matsakis, James M. Keller, Laurent Wendling, Jonathon Marjamaa, Ozy Sjahputera
2001 J jnl
Pattern Anal. Appl.
Dayou Wang, James M. Keller, C. Andrew Carson
2001 J jnl
IEEE Trans. Fuzzy Syst.
Paul D. Gader, James M. Keller, Bruce N. Nelson
2001 J jnl
IEEE Trans. Pattern Anal. Mach. Intell.
Jaesang Park, James M. Keller
2001 B conf
SMC
James M. Keller, Paul D. Gader, Sunghwan Sohn, Charles William Caldwell
2000 J jnl
Comput. Vis. Image Underst.
James M. Keller, Xiaomei Wang
2000 J jnl
Signal Process.
Paul D. Gader, Bruce N. Nelson, Hichem Frigui, Gary Vaillette, James M. Keller
2000 J jnl
Mach. Vis. Appl.
Mohamed A. Khabou, Paul D. Gader, James M. Keller
2000 B conf
FUZZ-IEEE
James M. Keller, Sansanee Auephanwiriyakul, Allyson D. Adrian
1999 J jnl
IEEE Trans. Syst. Man Cybern. Part A
Swarup Medasani, Raghu Krishnapuram, James M. Keller
1999 J jnl
Fuzzy Sets Syst.
Xiaomei Wang, James M. Keller
1999 conf
CIRA
George Chronis, James M. Keller, Marjorie Skubic
1999 J jnl
IEEE Trans. Fuzzy Syst.
James C. Bezdek, James M. Keller, Raghu Krishnapuram, Ludmila I. Kuncheva, Nikhil R. Pal
1998 J jnl
IEEE Trans. Image Process.
Adil S. Balghonaim, James M. Keller
1998 conf
MedInfo
Mauricio Leon, James M. Keller
1998 J jnl
IEEE Trans. Medical Imaging
Ronald Joe Stanley, James M. Keller, Paul D. Gader, Charles William Caldwell
1998 J jnl
Pattern Anal. Appl.
Ronald Joe Stanley, James M. Keller, Paul D. Gader, Charles William Caldwell
1998 B conf
SMC
J. Park, James M. Keller, Paul D. Gader, R. A. Schuchard
1998 J jnl
Int. J. Intell. Syst.
Kuhu Pal, Nikhil R. Pal, James M. Keller
1998 J jnl
IEEE Trans. Syst. Man Cybern. Part B
Dayou Wang, James M. Keller, C. Andrew Carson, Kelly K. McAdo-Edwards, Craig W. Bailey
1997 J jnl
Fuzzy Sets Syst.
James M. Keller
1997 J jnl
Computer
Paul D. Gader, James M. Keller, Raghu Krishnapuram, Jung-Hsien Chiang, Magdi A. Mohamed
1996 J jnl
Fuzzy Sets Syst.
Bolin Yan, James M. Keller
1996 J jnl
J. Electronic Imaging
Paul D. Gader, Magdi A. Mohamed, James M. Keller
1996 J jnl
Pattern Recognit. Lett.
Paul D. Gader, Magdi A. Mohamed, James M. Keller
1996 J jnl
IEEE Trans. Fuzzy Syst.
Raghuram Krishnapuram, James M. Keller
1996 J jnl
Int. J. Approx. Reason.
James M. Keller, Jeffrey Osborn
1995 B conf
CBMS
James M. Keller, Paul D. Gader, Ozy Sjahputera, Charles William Caldwell, Tim Hui-Ming Huang
1995 J jnl
IEEE Trans. Fuzzy Syst.
Paul D. Gader, James M. Keller, Juliet Cai
1995 conf
ICNN
James M. Keller, Hong Yang
1995 conf
ICNN
James M. Keller, Dayou Wang, C. Andrew Carson, Kelly K. McAdoo, Craig W. Bailey
1994 J jnl
Int. J. Intell. Syst.
James M. Keller, Raghu Krishnapuram, Zhihong Chen, Olfa Nasraoui
1994 J jnl
IEEE Trans. Syst. Man Cybern.
Advait M. Mogre, Robert W. McLaren, James M. Keller, Raghu Krishnapuram
1993 J jnl
IEEE Trans. Fuzzy Syst.
Raghuram Krishnapuram, James M. Keller
1993 J jnl
IEEE Trans. Pattern Anal. Mach. Intell.
Susan S. Chen, James M. Keller, Richard M. Crownover
1993 J jnl
IEEE Trans. Fuzzy Syst.
Raghuram Krishnapuram, James M. Keller, Yibing Ma
1992 J jnl
Inf. Sci.
James M. Keller, Hossein Tahani
1992 J jnl
IEEE Trans. Neural Networks
James M. Keller, Raghu Krishnapuram, Frank Chung-Hoon Rhee
1992 J jnl
Int. J. Approx. Reason.
James M. Keller, Hossein Tahani
1991 J jnl
Int. J. Intell. Syst.
Asghar Nafarieh, James M. Keller
1990 J jnl
Int. J. Intell. Syst.
James M. Keller, Carl L. Carpenter
1990 J jnl
IEEE Trans. Syst. Man Cybern.
Hossein Tahani, James M. Keller
1990 J jnl
Int. J. Imaging Syst. Technol.
James M. Keller, Young-Bo Seo
1990 J jnl
Artif. Intell.
Susan S. Chen, James M. Keller, Richard M. Crownover
1989 B conf
SMC
Advait M. Mogre, Robert W. McLaren, James M. Keller
1989 J jnl
Comput. Vis. Graph. Image Process.
James M. Keller, Susan S. Chen, Richard M. Crownover
1988 B conf
Pattern Recognition
John Wootton, James M. Keller, Carl L. Carpenter, Gregory Hobson
1988 B conf
Pattern Recognition
James M. Keller, Hongjie Qiu
1988 J jnl
Int. J. Approx. Reason.
Asghar Nafarieh, James M. Keller
1988 J jnl
Int. J. Approx. Reason.
Hongjie Qiu, James M. Keller
1987 J jnl
IEEE Trans. Pattern Anal. Mach. Intell.
James M. Keller, Richard M. Crownover, Robert Yu Chen
1987 J jnl
IEEE Trans. Syst. Man Cybern.
James M. Keller, Gregory Hobson, John Wootton, Asghar Nafarieh, Kent Luetkemeyer
1986 J jnl
IEEE Trans. Computers
J. J. Thomas, James M. Keller, G. N. Larsen
1985 J jnl
IEEE Trans. Syst. Man Cybern.
James M. Keller, Michael R. Gray, James A. Givens
1985 J jnl
IEEE Trans. Pattern Anal. Mach. Intell.
James M. Keller, Douglas J. Hunt
redb/extractors/decompiler/_archive/DecompileGhidra.py
← Index redb/extractors/decompiler/_archive/DecompileGhidra.py python
from hashlib import sha256, md5
import inspect
import subprocess
import json
import os
import time
from datetime import datetime, timezone
from typing import Dict, List, Any, Optional

from dotenv import load_dotenv
from redb.extractors.enum import Tag
from redb.extractors.extractor import Extractor
import magic
import pefile
import ppdeep
import tlsh


class DecompileGhidra(Extractor):
    def __init__(
        self,
        filepath,
        log,
        exporters=None,
        index_prefix=None,
        elastic_index=None,
        known_benign=False,
        known_malicious=False,
        filetype=None,
    ):
        super().__init__(
            filepath,
            log,
            exporters,
            index_prefix,
            elastic_index,
            known_benign,
            known_malicious,
        )
        self.log.debug(inspect.currentframe().f_code.co_name)
        self.ghidra_path = os.getenv("GHIDRA_PATH", "/opt/ghidra")
        self.java_script_path = os.getenv(
            "GHIDRA_SCRIPT_PATH",
            "/opt/ghidra/Ghidra/Features/Base/ghidra_scripts/GhidraDecompilerScript.java",
        )
        self.analysis_results = None
        self.ghidra_process = None  # Track the current process
        self.project_path = None
        self.filetype = filetype

        # Convert TIMEOUT to integer with a default of 1200 seconds (20 minutes)
        try:
            self.TIMEOUT = int(os.getenv("GHIDRA_TIMEOUT", "1200"))
        except ValueError:
            self.log.warning(
                "Invalid GHIDRA_TIMEOUT value, using default of 1200 seconds"
            )
            self.TIMEOUT = 1200

        self.initialize_project()

    def __enter__(self):
        return self

    def __exit__(self, exc_type, exc_val, exc_tb):
        self.cleanup_run()

    def is_dotnet(self):
        try:
            if self.filetype == "pebin":
                file_type = magic.from_buffer(self.binary)
                if ".Net" in file_type:
                    return True
                pe = pefile.PE(self.filepath)
                for entry in pe.OPTIONAL_HEADER.DATA_DIRECTORY:
                    # IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR is typically 14
                    if (
                        entry.name == "IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR"
                        and entry.Size > 0
                    ):
                        return True
                return False
        except AttributeError as e:
            self.log.error(
                f"AttributeError error dotnet file {self.hash.sha256} Full error : {e}"
            )
            return False

    def cleanup_run(self):
        """Clean up after analysis."""
        try:
            if self.ghidra_process and self.ghidra_process.poll() is None:
                self.ghidra_process.terminate()
                try:
                    self.ghidra_process.wait(timeout=5)
                except subprocess.TimeoutExpired:
                    self.ghidra_process.kill()

            # Clean up project directory
            if self.project_path and os.path.exists(self.project_path):
                import shutil

                shutil.rmtree(self.project_path)
                self.log.debug(f"Cleaned up project directory: {self.project_path}")

            # Force garbage collection
            import gc

            gc.collect()
        except Exception as e:
            self.log.error(f"Error in cleanup: {e}")

    # @classmethod
    # def cleanup_batch(cls):
    #     """Clean up the persistent project at the end of a batch."""
    #     print(f"Cleaning up Ghidra project for batch")
    #     if cls._project_path and os.path.exists(cls._project_path):
    #         try:
    #             import shutil
    #             shutil.rmtree(cls._project_path)
    #             cls._project_initialized = False
    #             cls._project_path = None
    #         except Exception as e:
    #             print(f"Error cleaning up project: {e}")

    def _get_environment(self):
        """Setup and return the environment for Ghidra."""
        env = os.environ.copy()
        java_home = os.getenv("GHIDRA_JAVA_HOME", "/usr/lib/jvm/java-17-openjdk-amd64")
        env.update(
            {
                "JAVA_HOME": java_home,
                "PATH": f"{java_home}/bin:{env['PATH']}",
                "LD_LIBRARY_PATH": f"{java_home}/lib:{env.get('LD_LIBRARY_PATH', '')}",
            }
        )
        # Print environment variables for debugging
        self.log.debug(f"JAVA_HOME: {env['JAVA_HOME']}")
        self.log.debug(f"PATH: {env['PATH']}")
        self.log.debug(f"LD_LIBRARY_PATH: {env['LD_LIBRARY_PATH']}")

        return env

    def initialize_project(self):
        """Initialize a temporary Ghidra project for this file."""
        # Create unique project directory
        self.project_path = f"/tmp/ghidra_{os.path.basename(self.filepath)}_{str(int(time.time()))}_{os.getpid()}"
        os.makedirs(self.project_path, exist_ok=True)
        self.log.debug(f"Created temporary project at {self.project_path}")

        # Create a minimal initialization file
        init_file = os.path.join(self.project_path, ".init")
        with open(init_file, "wb") as f:
            f.write(bytes([0x7F, 0x45, 0x4C, 0x46]))  # Valid ELF header magic bytes

        # Initialize project with minimal file
        env = self._get_environment()
        cmd = [
            f"{self.ghidra_path}/support/analyzeHeadless",
            self.project_path,
            "TempProject",
            "-import",
            init_file,
        ]

        try:
            result = subprocess.run(cmd, env=env, capture_output=True, text=True)
            if result.returncode != 0:
                self.log.error(f"Failed to initialize project: {result.stderr}")
                raise RuntimeError("Project initialization failed")

            # Clean up initialization file
            os.remove(init_file)
            self.log.debug("Project initialized successfully")

        except Exception as e:
            self.log.error(f"Error initializing project: {e}")
            raise

    def analyze_binary(self) -> Optional[Dict[str, Any]]:
        """Run Ghidra analysis and return results."""
        self.log.debug("Starting binary analysis")

        # # Check if packed
        # if self.check_binary_protection():
        #     self.log.warning("Skipping protected binary")
        #     return None

        # Check for .NET only if needed
        # if self.is_dotnet():
        #     self.MAX_NAMED_ARG_WARNINGS = 10000  # Higher threshold for .NET
        #     self.log.info("Adjusting parameters for .NET binary")
        # else:
        #     self.MAX_NAMED_ARG_WARNINGS = 1000  # Normal threshold

        if not os.path.exists(self.java_script_path):
            self.log.error(f"Java script not found: {self.java_script_path}")
            return None

        env = self._get_environment()

        try:
            base_cmd = [
                f"{self.ghidra_path}/support/analyzeHeadless",
                self.project_path,
                "TempProject",
                "-import",
                self.filepath,
                "-scriptPath",
                os.path.dirname(self.java_script_path),
                "-postScript",
                self.java_script_path,
                self.sha256,
                self.filepath,
            ]
            return self.run_ghidra(base_cmd, env)

        except Exception as e:
            self.log.error(f"Error in Ghidra analysis: {e}")
            return None

        finally:
            self.cleanup_run()

    def run_ghidra(
        self, cmd: list, env: Optional[Dict[str, str]] = None
    ) -> Optional[Dict[str, Any]]:
        """Run Ghidra process and capture JSON output with improved logging separation."""
        process = None
        try:
            self.log.info(f"Starting Ghidra analysis: {' '.join(cmd)}")
            start_time = time.time()

            process = subprocess.Popen(
                cmd, env=env, stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True
            )
            self.ghidra_process = process

            warning_counter = 0
            named_arg_counter = 0
            # Read all output lines
            json_output = None
            while True:
                line = process.stdout.readline()
                if not line and process.poll() is not None:
                    break

                stripped_line = line.strip()
                if not stripped_line:
                    continue

                # if 'Invalid FieldOrProp value in NamedArg' in stripped_line:
                #     named_arg_counter += 1
                #     if named_arg_counter > self.MAX_NAMED_ARG_WARNINGS:
                #         self.log.error(f"Too many NamedArg warnings ({named_arg_counter}), possible protected file.")
                #         self.ghidra_process.kill()
                #         return None
                if (
                    stripped_line.startswith("{")
                    and '"sha256"' in stripped_line
                    and '"decompiled"' in stripped_line
                ):
                    # This is our actual JSON output from GhidraDecompilerScript
                    json_output = stripped_line
                elif any(level in stripped_line for level in ["INFO", "WARN", "ERROR"]):
                    # Ghidra framework logging
                    log_level = (
                        "debug"
                        if "INFO" in stripped_line
                        else "warning"
                        if "WARN" in stripped_line
                        else "error"
                    )
                    if log_level == "warning" and any(
                        expected in stripped_line
                        for expected in [
                            "Unable to disassemble EXTERNAL block",
                            "Failed to markup ELF Note",
                            "Invalid FieldOrProp value in NamedArg",
                            "Unable to resolve constructor",
                            "Could not follow disassembly flow into non-existing memory",
                            "Unable to read bytes at ram",
                        ]
                    ):
                        # Skip expected warnings
                        continue

                    getattr(self.log, log_level)(f"Ghidra info: {stripped_line}")

            # Process completion and stderr
            try:
                stderr = process.stderr.read()
                process.wait(timeout=self.TIMEOUT)

                if stderr:
                    for line in stderr.splitlines():
                        stripped_line = line.strip()
                        if not stripped_line:
                            continue
                        if "ERROR" in stripped_line:
                            self.log.error(f"Ghidra stderr: {stripped_line}")
                        elif "WARN" in stripped_line:
                            self.log.warning(f"Ghidra stderr: {stripped_line}")
                        else:
                            self.log.debug(f"Ghidra stderr: {stripped_line}")

            except subprocess.TimeoutExpired:
                process.kill()
                self.log.error("Ghidra analysis timed out")
                return None

            elapsed_time = time.time() - start_time
            self.log.debug(f"Ghidra analysis completed in {elapsed_time:.2f}s")

            # Parse JSON output if we found it
            if json_output:
                try:
                    result = json.loads(json_output)
                    # Validate the required structure
                    if not isinstance(result, dict) or not all(
                        k in result
                        for k in ["sha256", "decompiled", "disassembled", "cfg"]
                    ):
                        self.log.error("Invalid JSON structure from Ghidra")
                        return None
                    return result
                except json.JSONDecodeError as e:
                    self.log.error(f"Failed to parse Ghidra JSON output: {e}")
                    return None
            else:
                self.log.error("No JSON output received from Ghidra")
                return None

        except Exception as e:
            self.log.error(f"Error running Ghidra: {str(e)}")
            if hasattr(e, "__traceback__"):
                import traceback

                self.log.debug(
                    f"Traceback: {''.join(traceback.format_tb(e.__traceback__))}"
                )
            return None

        finally:
            if process:
                try:
                    # Ensure pipes are closed
                    if process.stdout:
                        process.stdout.close()
                    if process.stderr:
                        process.stderr.close()
                    # Terminate process if still running
                    if process.poll() is None:
                        process.terminate()
                        try:
                            process.wait(timeout=5)
                        except subprocess.TimeoutExpired:
                            process.kill()
                except Exception as e:
                    self.log.error(f"Error cleaning up Ghidra process: {e}")

    def extract(self) -> bool:
        """Extract and process all analysis results."""
        self.log.debug(inspect.currentframe().f_code.co_name)
        try:
            results = self.analyze_binary()
            if not results:
                return False

            self.analysis_results = results
            return True

        except Exception as e:
            self.log.error(f"Error in extraction: {e}")
            return False

    def prepare_export_data(self, exporter_type: str) -> Any:
        """Prepare data for database export."""
        self.log.debug(inspect.currentframe().f_code.co_name)
        if not self.analysis_results:
            return None

        if exporter_type == "ClickHouseExporter":
            now = datetime.now(timezone.utc)

            def prepare_array_field(value, array_type):
                """Helper to prepare array fields with proper null handling"""
                if value is None:
                    return []
                return value

            def ssdeep_disassembly(func):
                try:
                    if len(func) > 1:
                        return ppdeep.hash(func)
                    return ""
                except Exception as e:
                    self.log.error(f"Error in disassembly ssdeep hash calculation: {e}")
                    return ""

            def tlsh_disassembly(func):
                try:
                    if len(func) >= 50:
                        return tlsh.hash(func.encode("utf-8"))
                    return ""
                except Exception as e:
                    self.log.error(f"Error in disassembly tlsh hash calculation: {e}")
                    return ""

            return {
                "multi_table": True,
                "decompiled_content": {
                    "table": "decompiled_functions_content",
                    "data": [
                        [
                            f["decompiled_content_hash"],
                            f["decompiled_function"],
                            f["function_type"],
                            now,
                        ]
                        for f in self.analysis_results["decompiled"]
                    ],
                    "column_names": [
                        "decompiled_content_hash",
                        "decompiled_function",
                        "function_type",
                        "analysis_date",
                    ],
                    "column_type_names": [
                        "FixedString(64)",
                        "String",
                        "Enum8('USER'=1, 'LIBRARY'=2, 'THUNK'=3, 'EXTERNAL'=4, 'UNKNOWN'=5)",
                        "DateTime64(3, 'UTC')",
                    ],
                },
                "decompiled_refs": {
                    "table": "decompiled_functions_references",
                    "data": [
                        [
                            self.analysis_results["sha256"],
                            f["decompiled_content_hash"],
                            f["decompiled_function_name"],
                            f["decompiled_function_address"],
                            now,
                        ]
                        for f in self.analysis_results["decompiled"]
                    ],
                    "column_names": [
                        "sha256",
                        "decompiled_content_hash",
                        "decompiled_function_name",
                        "decompiled_function_address",
                        "analysis_date",
                    ],
                    "column_type_names": [
                        "FixedString(64)",
                        "FixedString(64)",
                        "LowCardinality(String)",
                        "String",
                        "DateTime64(3, 'UTC')",
                    ],
                },
                "disassembled_content": {
                    "table": "disassembled_functions_content",
                    "data": [
                        [
                            f["disassembled_content_hash"],
                            f["fully_normalized_content_hash"],
                            f["api_normalized_content_hash"],
                            f["category_normalized_content_hash"],
                            f.get("disassembled_function", ""),
                            f.get("fully_normalized_disassembly", ""),
                            f.get("api_normalized_disassembly", ""),
                            f.get("category_normalized_disassembly", ""),
                            ssdeep_disassembly(f.get("disassembled_function", "")),
                            tlsh_disassembly(f.get("disassembled_function", "")),
                            ssdeep_disassembly(
                                f.get("fully_normalized_disassembly", "")
                            ),
                            tlsh_disassembly(f.get("fully_normalized_disassembly", "")),
                            f.get("function_type", "UNKNOWN"),
                            f.get("instruction_count", 0),
                            prepare_array_field(
                                f.get("instruction_types"), "LowCardinality(String)"
                            ),
                            f.get("control_flow_count", 0),
                            prepare_array_field(
                                f.get("memory_access_pattern"), "LowCardinality(String)"
                            ),
                            prepare_array_field(
                                f.get("register_usage"), "LowCardinality(String)"
                            ),
                            f.get("data_references_count", 0),
                            # prepare_array_field(f.get('opcode_frequency_vector'), 'Float32'),
                            # prepare_array_field(f.get('api_calls_vector'), 'Float32'),
                            # prepare_array_field(f.get('minhash_signature'), 'UInt64'),
                            # f.get('pic_hash', ''),
                            f.get("max_block_size", 0),
                            f.get("num_calls", 0),
                            f.get("stack_size", 0),
                            # prepare_array_field(f.get('instruction_type_ratios'), 'Float32'),
                            # prepare_array_field(f.get('instruction_embedding'), 'Float32'),
                            now,
                        ]
                        for f in self.analysis_results["disassembled"]
                    ],
                    "column_names": [
                        "disassembled_content_hash",
                        "fully_normalized_content_hash",
                        "api_normalized_content_hash",
                        "category_normalized_content_hash",
                        "disassembled_function",
                        "fully_normalized_disassembly",
                        "api_normalized_disassembly",
                        "category_normalized_disassembly",
                        "ssdeep_disassembly",
                        "tlsh_disassembly",
                        "ssdeep_fully_normalized",
                        "tlsh_fully_normalized",
                        "function_type",
                        "instruction_count",
                        "instruction_types",
                        "control_flow_count",
                        "memory_access_pattern",
                        "register_usage",
                        "data_references_count",
                        # 'opcode_frequency_vector',
                        # 'api_calls_vector',
                        # 'minhash_signature',
                        # 'pic_hash',
                        "max_block_size",
                        "num_calls",
                        "stack_size",
                        # 'instruction_type_ratios',
                        # 'instruction_embedding',
                        "analysis_date",
                    ],
                    "column_type_names": [
                        "FixedString(64)",
                        "FixedString(64)",
                        "FixedString(64)",
                        "FixedString(64)",
                        "String",
                        "String",
                        "String",
                        "String",
                        "Nullable(String)",
                        "Nullable(FixedString(72))",
                        "Nullable(String)",
                        "Nullable(FixedString(72))",
                        "Enum8('USER'=1, 'LIBRARY'=2, 'THUNK'=3, 'EXTERNAL'=4, 'UNKNOWN'=5)",
                        "UInt32",
                        "Array(LowCardinality(String))",
                        "UInt32",
                        "Array(LowCardinality(String))",
                        "Array(LowCardinality(String))",
                        "UInt32",
                        # 'Array(Float32)',
                        # 'Array(Float32)',
                        # 'Array(UInt64)',
                        # 'Nullable(FixedString(16))',
                        "Nullable(UInt32)",
                        "Nullable(UInt32)",
                        "Nullable(Int32)",
                        # 'Array(Float32)',
                        # 'Array(Float32)',
                        "DateTime64(3, 'UTC')",
                    ],
                },
                "disassembled_refs": {
                    "table": "disassembled_functions_references",
                    "data": [
                        [
                            self.analysis_results["sha256"],
                            f["disassembled_content_hash"],
                            f["fully_normalized_content_hash"],
                            f["api_normalized_content_hash"],
                            f["category_normalized_content_hash"],
                            f["disassembled_function_name"],
                            f["disassembled_function_address"],
                            now,
                        ]
                        for f in self.analysis_results["disassembled"]
                    ],
                    "column_names": [
                        "sha256",
                        "disassembled_content_hash",
                        "fully_normalized_content_hash",
                        "api_normalized_content_hash",
                        "category_normalized_content_hash",
                        "disassembled_function_name",
                        "disassembled_function_address",
                        "analysis_date",
                    ],
                    "column_type_names": [
                        "FixedString(64)",
                        "FixedString(64)",
                        "FixedString(64)",
                        "FixedString(64)",
                        "FixedString(64)",
                        "LowCardinality(String)",
                        "String",
                        "DateTime64(3, 'UTC')",
                    ],
                },
                "cfg_blocks": {
                    "table": "cfg_blocks",
                    "data": [
                        [
                            b["block_id"],
                            self.analysis_results["sha256"],
                            b["function_address"],
                            b["block_start_address"],
                            b["block_end_address"],
                            b["block_size"],
                            b["block_instructions"],
                            b["fully_normalized_instructions"],
                            b["api_normalized_instructions"],
                            b["category_normalized_instructions"],
                            b.get("predecessor_blocks", []),
                            b.get("successor_blocks", []),  # Use empty array as default
                            b.get("is_entry_block", False),
                            b.get("is_exit_block", False),
                            b.get("branch_type", "UNKNOWN"),
                            b.get("referenced_constants", []),
                            b.get("sign", 1),  # Use 1 as default for sign
                            now,
                        ]
                        for b in self.analysis_results["cfg"]
                    ],
                    "column_names": [
                        "block_id",
                        "sha256",
                        "function_address",
                        "block_start_address",
                        "block_end_address",
                        "block_size",
                        "block_instructions",
                        "fully_normalized_instructions",
                        "api_normalized_instructions",
                        "category_normalized_instructions",
                        "predecessor_blocks",
                        "successor_blocks",
                        "is_entry_block",
                        "is_exit_block",
                        "branch_type",
                        "referenced_constants",
                        "sign",
                        "analysis_date",
                    ],
                    "column_type_names": [
                        "FixedString(64)",
                        "FixedString(64)",
                        "String",
                        "String",
                        "String",
                        "UInt32",
                        "String",
                        "Nullable(String)",
                        "Nullable(String)",
                        "Nullable(String)",
                        "Array(String)",
                        "Array(String)",
                        "Bool",
                        "Bool",
                        "Enum8('DIRECT'=1, 'CONDITIONAL'=2, 'CALL'=3, 'RETURN'=4, 'FALLTHROUGH'=5, 'UNKNOWN'=6)",
                        "Array(String)",
                        "Int8",
                        "DateTime64(3, 'UTC')",
                    ],
                },
                "function_analysis_errors": {
                    "table": "function_analysis_errors",
                    "data": [
                        [
                            self.analysis_results["sha256"],
                            f["function_name"],
                            f["function_address"],
                            f["error_location"],
                            f.get(
                                "error_message", ""
                            ),  # it could be empty, how to handle it?
                            f.get("error_details", ""),
                            f.get("error_type", "unknown"),
                            md5(
                                f"{f['error_message']}{f['function_name']}{f['function_address']}{f['error_location']}".encode()
                            ).hexdigest(),
                            "new",
                            now,
                        ]
                        for f in self.analysis_results["errors"]
                    ],
                    "column_names": [
                        "sha256",
                        "function_name",
                        "function_address",
                        "error_location",
                        "error_message",
                        "error_details",
                        "error_type",
                        "error_hash",
                        "status",
                        "analysis_date",
                    ],
                    "column_type_names": [
                        "FixedString(64)",
                        "Nullable(String)",
                        "String",
                        "LowCardinality(String)",
                        "Nullable(String)",
                        "Nullable(String)",
                        "Nullable(String)",
                        "FixedString(32)",
                        "Enum8('new'=1, 'investigating'=2, 'fixed'=3, 'wontfix'=4)",
                        "DateTime64(3, 'UTC')",
                    ],
                },
            }

    def tag(self) -> str:
        """Return the tag for this extractor."""
        return Tag.DECOMPILED.value

    def get_clickhouse_table(self) -> str:
        """Not used directly as we're handling multiple tables."""
        pass